{"openapi":"3.1.0","info":{"title":"graph8 Developer API","description":"Public API for programmatic access to graph8 data. Authenticate with an org API key: `Authorization: Bearer <api_key>`","version":"1.0.0"},"servers":[{"url":"/api/v1"},{"url":"https://be.graph8.com/api/v1","description":"Production"},{"url":"https://be.qa.graph8.com/api/v1","description":"QA"}],"paths":{"/app-sessions/exchange":{"post":{"tags":["App Platform - Tokens"],"summary":"Exchange App Session","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nMint a short-lived browser app token for the authenticated PropelAuth principal.\n\nAuth is the EXISTING ``get_current_user`` PropelAuth dependency — no valid\nprincipal -> 401. ``subject`` / ``client_org_id`` / ``role`` are derived\nSERVER-SIDE from that validated principal (``derive_browser_identity``), never\nfrom ``body`` — a forged identity/role in the body has no effect. Minting also\nrequires a consented installation of the target app in the principal's org (403).\nA fail-closed per-principal / per-app limiter throttles the mint (429).","operationId":"exchange_app_session_app_sessions_exchange_post","security":[{"HTTPBearer":[]}],"parameters":[{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"The organization ID to use for the request","title":"X-Org-Id"},"description":"The organization ID to use for the request"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BrowserExchangeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TokenResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-lifecycle":"preview","x-graph8-enabled-by":"M6_APP_TOKENS_ENABLED"}},"/service-token":{"post":{"tags":["App Platform - Tokens"],"summary":"Issue Service Token","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nMint a service (client-credentials) app token bound to the credential's org.\n\nA fail-closed per-credential limiter throttles the mint (429) before the\ncredential is even checked, so brute-forcing a client secret is rate-bound.","operationId":"issue_service_token_service_token_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ServiceTokenRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TokenResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-lifecycle":"preview","x-graph8-enabled-by":"M6_APP_TOKENS_ENABLED"}},"/app-platform/.well-known/jwks.json":{"get":{"tags":["App Platform - Tokens"],"summary":"App Token Jwks","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nServe the public JWKS (all kids). Empty keyset when dormant.","operationId":"app_token_jwks_app_platform__well_known_jwks_json_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"additionalProperties":true,"type":"object","title":"Response App Token Jwks App Platform  Well Known Jwks Json Get"}}}}},"x-graph8-tier":"read","x-graph8-lifecycle":"preview","x-graph8-enabled-by":"M6_APP_TOKENS_ENABLED"}},"/contacts/{contact_id}/suppression":{"get":{"tags":["Suppressions"],"summary":"Check Contact Suppression","description":"Is this contact suppressed, and on which channel(s)?\n\nReads the SAME central ledger every send path checks\n(``apps.suppression().service().list_suppressions``), so a \"not\nsuppressed\" answer here means the same thing it means to the sequencer\nand newsletter send gates.","operationId":"check_contact_suppression_contacts__contact_id__suppression_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact ID (mashup_contacts.id)","title":"Contact Id"},"description":"Contact ID (mashup_contacts.id)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SuppressionStatusResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/suppressions":{"get":{"tags":["Suppressions"],"summary":"List Suppressions","description":"Paginated org-wide list of active suppressions.\n\nUnlike the app's Data -> Suppressions grid (which joins contact/company\nnames for display), this is the raw ledger -- no PII, see module\ndocstring. Resolve a row's contact via ``GET /contacts/{contact_id}``.","operationId":"list_suppressions_contacts_suppressions_get","parameters":[{"name":"channel","in":"query","required":false,"schema":{"anyOf":[{"enum":["all","email","phone","linkedin"],"type":"string"},{"type":"null"}],"description":"Filter: all | email | phone | linkedin","title":"Channel"},"description":"Filter: all | email | phone | linkedin"},{"name":"category","in":"query","required":false,"schema":{"anyOf":[{"enum":["contact_initiated","org_initiated","system"],"type":"string"},{"type":"null"}],"description":"Filter: contact_initiated | org_initiated | system","title":"Category"},"description":"Filter: contact_initiated | org_initiated | system"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_SuppressionRecord__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/suppress":{"post":{"tags":["Suppressions"],"summary":"Suppress Contact","description":"Stop all outreach to a contact. Proxies the SAME handler the in-app\ncontact view's \"Suppress\" action calls (``contacts/router.py:1660``) --\nchannel=all, category=org_initiated, honoured by every surface that\nreads the central ledger (sequencer, newsletter, audience_sync).","operationId":"suppress_contact_contacts__contact_id__suppress_post","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact ID (mashup_contacts.id)","title":"Contact Id"},"description":"Contact ID (mashup_contacts.id)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuppressContactRequest","default":{}}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SuppressActionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/unsuppress":{"post":{"tags":["Suppressions"],"summary":"Unsuppress Contact","description":"Reverse an operator suppression. Proxies the SAME handler the in-app\ncontact view's \"Unsuppress\" action calls (``contacts/router.py:1702``).\nClears ONLY the org_initiated umbrella -- an independent\ncontact_initiated (they-asked) or system (bounce/complaint) opt-out is\nnever overridden through this endpoint, matching the app exactly.","operationId":"unsuppress_contact_contacts__contact_id__unsuppress_post","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact ID (mashup_contacts.id)","title":"Contact Id"},"description":"Contact ID (mashup_contacts.id)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuppressContactRequest","default":{}}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_UnsuppressActionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/suppressions/bulk-add":{"post":{"tags":["Suppressions"],"summary":"Bulk Add Suppressions","description":"Suppress an explicit set of contacts in one call. Proxies the SAME\nhandler the app's Lists -> add-to-suppressions bulk action calls\n(``contacts/router.py:1819``), minus the list/filter-model resolution\n(a UI concept) -- pass the contact PKs you already have. Idempotent:\nalready-active rows are left untouched.","operationId":"bulk_add_suppressions_contacts_suppressions_bulk_add_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuppressionsBulkAddRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BulkSuppressResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/suppressions/reinstate":{"post":{"tags":["Suppressions"],"summary":"Reinstate Suppressions","description":"Bulk-reinstate contacts. Proxies the SAME handler the app's\nSuppressions grid \"Reinstate\" bulk action calls\n(``contacts/router.py:1771``). ``operator_reversible`` is recomputed\nserver-side per contact; a contact whose only active suppression is\ncontact_initiated or system is skipped and reported, never reinstated.","operationId":"reinstate_suppressions_contacts_suppressions_reinstate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuppressionsReinstateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BulkReinstateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/column-definitions":{"get":{"tags":["Contacts"],"summary":"List Contact Column Definitions","description":"Every column the grid can show, with its type and display name.\n\nThe richest of the schema reads here: it carries base columns, custom\ncolumns and enrichment columns together. `GET /contacts/columns` returns\nthe custom columns alone.","operationId":"list_contact_column_definitions_contacts_column_definitions_get","parameters":[{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Include the columns specific to this list. The list also decides whether contact or company columns are returned - a companies list returns company columns from this contacts path.","title":"List Id"},"description":"Include the columns specific to this list. The list also decides whether contact or company columns are returned - a companies list returns company columns from this contacts path."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/custom-column-definitions":{"get":{"tags":["Contacts"],"summary":"List Custom Column Definitions","description":"The org's custom columns as `{column_id, name}` pairs.\n\nThe flat form: enough to build a field picker, and the source of the ids\nother calls accept.","operationId":"list_custom_column_definitions_contacts_custom_column_definitions_get","parameters":[{"name":"entity_type","in":"query","required":false,"schema":{"type":"string","description":"`contact` or `company`. Anything else is refused.","default":"contact","title":"Entity Type"},"description":"`contact` or `company`. Anything else is refused."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/searchable-fields":{"get":{"tags":["Contacts"],"summary":"List Searchable Fields","description":"Which fields can be searched, and what each one COSTS.\n\nEvery entry carries a `tier` derived from the org's real indexes -\n`fast`, `text_search` or `full_scan` - plus the operators that column's\nlive type supports. Index coverage is per-org, so this is the only honest\nway to know a custom-column search is a full table scan before running it.","operationId":"list_searchable_fields_contacts_searchable_fields_get","parameters":[{"name":"entity_type","in":"query","required":false,"schema":{"type":"string","description":"`contact` or `company`. Anything else is refused.","default":"contact","title":"Entity Type"},"description":"`contact` or `company`. Anything else is refused."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/base-columns":{"get":{"tags":["Contacts"],"summary":"List Base Columns","description":"The real DATABASE columns behind a list.\n\nExcludes the composite and enrichment columns the grid displays, so what\ncomes back is what can actually be written to and filtered on.","operationId":"list_base_columns_contacts_base_columns_get","parameters":[{"name":"list_id","in":"query","required":true,"schema":{"type":"integer","description":"Required: the list decides which base columns exist.","title":"List Id"},"description":"Required: the list decides which base columns exist."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/column-names":{"get":{"tags":["Contacts"],"summary":"List Column Names","description":"Column names only, as a flat list of strings.","operationId":"list_column_names_contacts_column_names_get","parameters":[{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Include this list's own columns.","title":"List Id"},"description":"Include this list's own columns."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/form-fields":{"get":{"tags":["Contacts"],"summary":"Get Contact Form Fields","description":"Fields grouped the way the contact form presents them.\n\nSame underlying columns as the schema reads above, arranged into labelled\ngroups with a `required` flag - what to render, rather than what exists.","operationId":"get_contact_form_fields_contacts_form_fields_get","parameters":[{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Include this list's custom fields.","title":"List Id"},"description":"Include this list's custom fields."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/dashboard-stats":{"get":{"tags":["Contacts"],"summary":"Get Contact Dashboard Stats","description":"Counts and distributions across the contacts this key can see.\n\nScoped, not org-wide: a key narrowed away from contacts gets its own\nnarrower totals rather than the organisation's.","operationId":"get_contact_dashboard_stats_contacts_dashboard_stats_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/fetch":{"post":{"tags":["Contacts"],"summary":"Fetch Contacts","description":"Page through contacts, projecting only the columns you name.\n\nA POST because the filter is a body, not because it writes: this reads and\nmutates nothing, and is tiered as a read so a read-only key can call it.\n\nPrefer this over `GET /contacts` when you want a narrow column set -\nnaming the columns lets the planner drop joins the full row forces.","operationId":"fetch_contacts_contacts_fetch_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FetchContactsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/profile-pictures":{"post":{"tags":["Contacts"],"summary":"Get Contact Profile Pictures","description":"Resolve profile photos for a batch of LinkedIn URLs.\n\nA missing key in the result means \"no allow-listed photo for that URL\",\nnot \"the lookup failed\" - roughly half of contacts have one. Soft-fails to\nan empty map rather than erroring, so it is safe on a render path.","operationId":"get_contact_profile_pictures_contacts_profile_pictures_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProfilePicturesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/column-values":{"post":{"tags":["Contacts"],"summary":"Get Record Column Values","description":"Every column value for one row, resolved through a list.\n\nThe list is required, not optional: it decides whether `record_id` names a\ncontact or a company and which list-scoped custom columns apply. Reading\nthe same id through two different lists can legitimately return different\ncolumns.","operationId":"get_record_column_values_contacts_column_values_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RecordColumnValuesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/bulk-update":{"post":{"tags":["Contacts"],"summary":"Bulk Update Contacts","description":"Apply a DIFFERENT change to each of many contacts.\n\nThe whole target set is authorised before the first write, so a batch\ncontaining one contact the key cannot write is refused outright rather\nthan half-applied.\n\nAfter that preflight, individual failures are REPORTED, not fatal: read\n`updated`, `failed` and the per-contact `errors` rather than the HTTP\nstatus.","operationId":"bulk_update_contacts_contacts_bulk_update_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"array","items":{"type":"object","additionalProperties":true},"description":"One object per contact. Each MUST carry `id`; every other key is a field to set on that contact.","title":"Updates"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/assign-owner":{"post":{"tags":["Contacts"],"summary":"Assign Contact Owner","description":"Set the owner on EVERY contact matching a selection.\n\nThe selection is resolved server-side, so the number of contacts affected\nis not bounded by anything in the request. A null `owner_id` UNASSIGNS\nthem all.","operationId":"assign_contact_owner_contacts_assign_owner_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssignOwnerMatchingRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/merge-filtered":{"post":{"tags":["Contacts"],"summary":"Merge Filtered Contacts","description":"Add every contact matching a filter into `target_list_id`.\n\nDespite the name this does NOT merge duplicate contacts together - it\nmerges a SELECTION INTO A LIST. `/duplicates` is the surface that merges\nrecords.\n\nA 409 means some contacts need a decision before they can be added; re-send\nwith `conflict_resolution`. Blocked contacts are never added regardless.","operationId":"merge_filtered_contacts_contacts_merge_filtered_post","parameters":[{"name":"filterModel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Optional per-column filter JSON, applied alongside `filter`.","title":"Filtermodel"},"description":"Optional per-column filter JSON, applied alongside `filter`."},{"name":"sortModel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Optional sort JSON.","title":"Sortmodel"},"description":"Optional sort JSON."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MergeFilteredRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/withdraw-from-sequences":{"post":{"tags":["Contacts"],"summary":"Withdraw Contacts From Sequences","description":"Take contacts OUT of a sequence. They stop receiving its steps.\n\n`remove_all=true` withdraws them from EVERY sequence they are enrolled in\nand ignores `sequence_id` - the wider blast radius of the two, and never\nthe default.\n\n`response` is REQUIRED by the app handler rather than decoration: it sets\na status on it for the partial-withdrawal case, so omitting it is an\nAttributeError on every call.","operationId":"withdraw_contacts_from_sequences_contacts_withdraw_from_sequences_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WithdrawFromSequencesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/verify-email":{"post":{"tags":["Contacts"],"summary":"Verify Contact Emails","description":"Re-check deliverability for a batch of contacts. SPENDS CREDITS.\n\nSynchronous: one call to the verification service, and the result is\nwritten back onto each contact. Capped at 1000 contacts - use\n`/contacts/verify-email/async` for a whole list.\n\nDifferent from `POST /enrichment/verify-email`, which checks one arbitrary\naddress and stores nothing.","operationId":"verify_contact_emails_contacts_verify_email_post","parameters":[{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Restrict a filtered selection to this list.","title":"List Id"},"description":"Restrict a filtered selection to this list."},{"name":"filterModel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Per-column filter JSON. With `list_id`, verifies every matching contact instead of the ids in the body.","title":"Filtermodel"},"description":"Per-column filter JSON. With `list_id`, verifies every matching contact instead of the ids in the body."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VerifyContactEmailRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/contacts/verify-email/async":{"post":{"tags":["Contacts"],"summary":"Verify Contact Emails Async","description":"Queue verification for a whole list or filtered selection. SPENDS CREDITS.\n\nReturns the number of contacts and addresses ACCEPTED, not verified - the\nresults land on the contacts as the job runs. `all_matching` resolves the\nselection server-side, so the cost is not bounded by anything in the\nrequest; send the filter you actually mean.","operationId":"verify_contact_emails_async_contacts_verify_email_async_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VerifyContactEmailAsyncRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/contacts/unlock-info":{"post":{"tags":["Contacts"],"summary":"Unlock Contact Info","description":"Reveal withheld contact details. CHARGES CREDITS.\n\nReturns `credits_charged`. Contacts already unlocked are not charged\nagain, so re-sending the same ids is safe - but `all_matching` resolves an\nunbounded selection, and every newly-unlocked contact in it is billed.","operationId":"unlock_contact_info_contacts_unlock_info_post","parameters":[{"name":"filterModel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Per-column filter JSON, resolved against `list_id`.","title":"Filtermodel"},"description":"Per-column filter JSON, resolved against `list_id`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UnlockContactInfoRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/engagement-summary":{"get":{"tags":["Contacts"],"summary":"Get Contact Engagement Summary","description":"How much this contact has engaged: emails, calls, meetings, visits.\n\nGated on `id_kind=\"pk\"` because the handler counts against\n`mashup_contacts.id`. A gate resolving any other namespace would authorise\na different row than it serves.","operationId":"get_contact_engagement_summary_contacts__contact_id__engagement_summary_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact primary key.","title":"Contact Id"},"description":"Contact primary key."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/sites-visited":{"get":{"tags":["Contacts"],"summary":"Get Contact Sites Visited","description":"Pages this contact visited on your site.","operationId":"get_contact_sites_visited_contacts__contact_id__sites_visited_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact primary key.","title":"Contact Id"},"description":"Contact primary key."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":730,"minimum":1,"description":"Lookback window. Bounded here rather than left open: the query is an unindexed analytics scan and an unbounded window is a cheap way to exhaust it.","default":90,"title":"Days"},"description":"Lookback window. Bounded here rather than left open: the query is an unindexed analytics scan and an unbounded window is a cheap way to exhaust it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/next-best-step":{"get":{"tags":["Contacts"],"summary":"Get Contact Next Best Step","description":"What to do next with this contact, and why. SPENDS CREDITS.\n\nA GET that costs money: the recommendation is generated by a model on a\ncache miss, and the cache key includes the contact's engagement state, so\nactivity on the record invalidates it. Tiered `billable` for that reason\nrather than as an ordinary read - polling it per contact is real spend.","operationId":"get_contact_next_best_step_contacts__contact_id__next_best_step_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact primary key.","title":"Contact Id"},"description":"Contact primary key."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/dashboard":{"get":{"tags":["Contacts"],"summary":"Get Contact Dashboard","description":"Everything the contact detail view shows, in one call.\n\nOpen-shaped: this is a composed view whose panels grow with the product.","operationId":"get_contact_dashboard_contacts__contact_id__dashboard_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact primary key.","title":"Contact Id"},"description":"Contact primary key."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/row-detail/{record_id}":{"get":{"tags":["Contacts"],"summary":"Get Contact Row Detail","description":"Which workflows have run against this record, and what they produced.\n\nCarries the execution timeline, each run's outputs, and the actions\ncurrently available on the row. The workflow-permission gate is the app's\nown, including its soak behaviour - while the enforcement flag is off a\ncaller without `workflows:read` is logged and allowed, because that\npermission is not yet held by every role.\n\nUnder `/contacts/` because the record scope it enforces is the CONTACT\none, but `record_id` is whatever the list holds: a companies list reads\ncompany rows through this path.","operationId":"get_contact_row_detail_contacts_row_detail__record_id__get","parameters":[{"name":"record_id","in":"path","required":true,"schema":{"type":"integer","description":"Record primary key.","title":"Record Id"},"description":"Record primary key."},{"name":"list_id","in":"query","required":true,"schema":{"type":"integer","description":"Required: the list the record is read through.","title":"List Id"},"description":"Required: the list the record is read through."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/documents/generate-all":{"post":{"tags":["Contacts"],"summary":"Generate All Contact Documents","description":"Generate the full document set for this contact. SPENDS CREDITS.\n\nEnqueues the work and returns immediately; poll\n`/contacts/{contact_id}/documents/generation-status` for progress. Each\ndocument is a model call, so calling this repeatedly on the same contact\nspends repeatedly.","operationId":"generate_all_contact_documents_contacts__contact_id__documents_generate_all_post","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact primary key.","title":"Contact Id"},"description":"Contact primary key."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/documents/generation-status":{"get":{"tags":["Contacts"],"summary":"Get Contact Generation Status","description":"Progress of this contact's document generation. Reads only.\n\nNamed for the app route it proxies, which means the path contains\n`generate` - the tier heuristic reads that as an active GET and would\npublish a status poll as a credit spend. It is corrected by an explicit\nentry in `build_scope_policy.py::READ_ONLY_ACTIVE_GET_ROUTES` rather than\nby spelling the path around the matcher.","operationId":"get_contact_generation_status_contacts__contact_id__documents_generation_status_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact primary key.","title":"Contact Id"},"description":"Contact primary key."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/documents/from-skill":{"post":{"tags":["Contacts"],"summary":"Save Skill Result To Contact","description":"Store a skill run's output on this contact as a document.","operationId":"save_skill_result_to_contact_contacts__contact_id__documents_from_skill_post","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact primary key.","title":"Contact Id"},"description":"Contact primary key."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SaveSkillResultRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/activity-feed":{"get":{"tags":["Contacts"],"summary":"Get Activity Feed","description":"One timeline over everything that happened to a record.\n\nReplaces four separate per-type reads. `entity_type` decides which record\nscope authorises the call, and all four are resolved from the CALLING\nKEY'S OWN credential scopes - so a key without `deals:read` resolves the\ndeal scope to nothing and cannot read a deal's feed through this path,\neven though the key gate on the route is `contacts:read`.","operationId":"get_activity_feed_activity_feed_get","parameters":[{"name":"entity_type","in":"query","required":true,"schema":{"type":"string","description":"contact | company | deal | team_member","title":"Entity Type"},"description":"contact | company | deal | team_member"},{"name":"entity_id","in":"query","required":true,"schema":{"type":"string","description":"Id of that record.","title":"Entity Id"},"description":"Id of that record."},{"name":"types","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated subset of task,note,email,call,meeting,sms,chat,stage_change,quote,record_change,deal. Omit for all.","title":"Types"},"description":"Comma-separated subset of task,note,email,call,meeting,sms,chat,stage_change,quote,record_change,deal. Omit for all."},{"name":"source","in":"query","required":false,"schema":{"type":"string","description":"manual | crm | system | dialer | automation | api | all","default":"all","title":"Source"},"description":"manual | crm | system | dialer | automation | api | all"},{"name":"since","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO 8601 cursor; returns events at or after it.","title":"Since"},"description":"ISO 8601 cursor; returns events at or after it."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/duplicates/settings/preview-detection-rule":{"post":{"tags":["Contacts"],"summary":"Preview Detection Rule","description":"Dry-run a duplicate-detection rule. Writes nothing.\n\nReturns the pair count the rule would match plus a small sample, which is\nthe only way to size a rule before auto-merge acts on it. A POST because\nthe rule is a body; tiered a read so a read-only key can check a rule\nbefore someone saves it.","operationId":"preview_detection_rule_duplicates_settings_preview_detection_rule_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PreviewDetectionRuleRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/duplicates/auto-merge":{"post":{"tags":["Contacts"],"summary":"Trigger Auto Merge","description":"Run auto-merge once. RECORDS ARE DESTROYED.\n\nEach merge removes one record and moves its data onto the survivor. The\nonly way back is `POST /duplicates/undo-merge/{merge_history_id}`, one\nmerge at a time. Send `dry_run=true` first.\n\nA 200 does NOT by itself mean anything merged: if the org has auto-merge\ndisabled or is in shadow mode the response says so instead of failing,\nwhich is the app's behaviour and is preserved here. Read the body.","operationId":"trigger_auto_merge_duplicates_auto_merge_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AutoMergeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"contacts:delete","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/timeline":{"get":{"tags":["Contacts"],"summary":"Get Contact Timeline","description":"The funnel timeline for one contact: what was done, what it cost, what came back.\n\nRead-only. Tenancy: the key's own organisation is the only schema read,\nand the contact must be visible to the key (`id_kind=\"pk\"`, the namespace\nthe timeline sources are keyed on, so the gate authorises the same row the\nhandler serves). Every step kind is present in a fixed order; `count` and\n`cost_credits` are `null` when not recorded, which is not the same as `0`.\nReturns 404 for a contact outside the key's organisation or visibility and\n504 when the read times out.","operationId":"get_contact_timeline_contacts__contact_id__timeline_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact primary key (`mashup_contacts.id`).","title":"Contact Id"},"description":"Contact primary key (`mashup_contacts.id`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/companies/review-stats":{"get":{"tags":["Companies"],"summary":"Get Company Review Stats","description":"How many companies and contacts are flagged as needing review.\n\nORG-WIDE counts. The app handler takes no record scope, so unlike the\nlisting beside it these totals are not narrowed to what the caller can\nsee - two keys with different record scopes get the same numbers.","operationId":"get_company_review_stats_companies_review_stats_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/enriched":{"get":{"tags":["Companies"],"summary":"List Companies Enriched","description":"Companies with their revenue and account overlays joined on.\n\n`GET /companies` returns the base record. This returns the same companies\nwith the ABM and revenue overlay fields - tier, score, owner, status -\ncoalesced in, which is what the account views are built from.","operationId":"list_companies_enriched_companies_enriched_get","parameters":[{"name":"skip","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Rows to skip.","default":0,"title":"Skip"},"description":"Rows to skip."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":10000,"minimum":1,"description":"Rows to return. The app defaults this to 10000 - the entire roster in one response. Defaulted to 100 here; raise it deliberately.","default":100,"title":"Limit"},"description":"Rows to return. The app defaults this to 10000 - the entire roster in one response. Defaulted to 100 here; raise it deliberately."},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Substring match on name or domain.","title":"Search"},"description":"Substring match on name or domain."},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by record status, e.g. `prospect`.","title":"Status"},"description":"Filter by record status, e.g. `prospect`."},{"name":"website_status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by website status.","title":"Website Status"},"description":"Filter by website status."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/contacts":{"get":{"tags":["Companies"],"summary":"List Contacts Across Companies","description":"Contacts across EVERY company, with their company and pipeline context.\n\nThe buying-committee view: `department`, `buying_role` and `in_pipeline`\nare not available on `GET /contacts`, and each row carries the company it\nbelongs to.\n\nPublished under `/companies` because that is the surface it belongs to,\nbut the rows it returns are CONTACTS and it is filtered by the CONTACT\nrecord scope. A key holding `companies:read` without contact visibility\nresolves that scope to nothing and gets an empty result rather than a\ncompany-scoped one - it fails closed, but it is worth knowing which of the\ntwo scopes actually governs the rows.","operationId":"list_contacts_across_companies_companies_contacts_get","parameters":[{"name":"skip","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Skip"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":10000,"minimum":1,"description":"The app defaults this to 10000; 100 here.","default":100,"title":"Limit"},"description":"The app defaults this to 10000; 100 here."},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Substring match on name or email.","title":"Search"},"description":"Substring match on name or email."},{"name":"department","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by job department.","title":"Department"},"description":"Filter by job department."},{"name":"buying_role","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by buying-committee role, e.g. `decision_maker`.","title":"Buying Role"},"description":"Filter by buying-committee role, e.g. `decision_maker`."},{"name":"in_pipeline","in":"query","required":false,"schema":{"type":"boolean","description":"Only contacts attached to an open deal.","default":false,"title":"In Pipeline"},"description":"Only contacts attached to an open deal."},{"name":"owner_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by contact owner.","title":"Owner Id"},"description":"Filter by contact owner."},{"name":"sort_by","in":"query","required":false,"schema":{"type":"string","description":"name | title | company_name | department | email | updated_at","default":"updated_at","title":"Sort By"},"description":"name | title | company_name | department | email | updated_at"},{"name":"sort_order","in":"query","required":false,"schema":{"type":"string","description":"asc | desc","default":"desc","title":"Sort Order"},"description":"asc | desc"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/form-fields":{"get":{"tags":["Companies"],"summary":"Get Company Form Fields","description":"Fields grouped the way the company form presents them.","operationId":"get_company_form_fields_companies_form_fields_get","parameters":[{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Include this list's custom fields.","title":"List Id"},"description":"Include this list's custom fields."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/import":{"post":{"tags":["Companies"],"summary":"Import Companies","description":"Create or update companies from a batch of contacts. SPENDS CREDITS.\n\nContacts are grouped by email domain: a new domain creates a company, a\nknown one is updated. Every NEW company then triggers the full\nintelligence pipeline - a site crawl, several model calls and a paid\nenrichment lookup - and every contact triggers a paid person lookup. One\nrequest with 50 domains and 500 contacts is 50 pipelines plus 550 provider\ncalls, so this is the most expensive operation on the company surface.\n\nThe body is REQUIRED here. The app declares it optional and then reads\n`data.contacts` unconditionally, so an empty request there is an\nAttributeError and a 500; requiring it makes the same request a 422.\n\nIndividual rows can fail without failing the call - read the response\nrather than the status.","operationId":"import_companies_companies_import_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ImportCompaniesRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/companies/assign-owner":{"post":{"tags":["Companies"],"summary":"Assign Company Owner","description":"Set the owner on EVERY company matching a selection.\n\nThe selection is resolved server-side, so the number of companies affected\nis not bounded by anything in the request. A null `owner_id` UNASSIGNS\nthem all.","operationId":"assign_company_owner_companies_assign_owner_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssignOwnerMatchingRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/companies/merge-filtered":{"post":{"tags":["Companies"],"summary":"Merge Filtered Companies","description":"Add every company matching a filter into `target_list_id`.\n\nDespite the name this does NOT merge duplicate companies together - it\nmerges a SELECTION INTO A LIST. `/duplicates` merges records.\n\nA 409 means some companies need a decision; re-send with\n`conflict_resolution`.","operationId":"merge_filtered_companies_companies_merge_filtered_post","parameters":[{"name":"filterModel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Optional per-column filter JSON.","title":"Filtermodel"},"description":"Optional per-column filter JSON."},{"name":"sortModel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Optional sort JSON.","title":"Sortmodel"},"description":"Optional sort JSON."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MergeFilteredRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/companies/{company_id}/billing-prefill":{"get":{"tags":["Companies"],"summary":"Get Company Billing Prefill","description":"Billing details discovered for this company, ready to prefill a quote.\n\n`status` is the field to read first: `ready` means the details are usable,\n`pending` means discovery has not finished, `empty` means nothing was\nfound. Reads only - it does not trigger discovery.","operationId":"get_company_billing_prefill_companies__company_id__billing_prefill_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/people":{"get":{"tags":["Companies"],"summary":"List Company People","description":"The people at this company, with their buying-committee roles.\n\nOverlaps `GET /companies/{company_id}/contacts`, which returns the same\npeople as contact records. This one is the account-team view: the roles\nand engagement scoring the ABM surface reads.","operationId":"list_company_people_companies__company_id__people_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/workflow-status":{"get":{"tags":["Companies"],"summary":"Get Company Workflow Status","description":"Where this company's intelligence and synthesis workflows stand.","operationId":"get_company_workflow_status_companies__company_id__workflow_status_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"include_documents","in":"query","required":false,"schema":{"type":"boolean","description":"Also list the documents each workflow produced.","default":false,"title":"Include Documents"},"description":"Also list the documents each workflow produced."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/synthesis-readiness":{"get":{"tags":["Companies"],"summary":"Get Company Synthesis Readiness","description":"Whether synthesis can run yet, and what is blocking it.\n\nWorth calling before `retry-synthesis`: `blocking_issues` names what is\nmissing, and retrying without fixing it spends credits to fail again.","operationId":"get_company_synthesis_readiness_companies__company_id__synthesis_readiness_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/intelligence-steps":{"get":{"tags":["Companies"],"summary":"Get Company Intelligence Steps","description":"Per-step state of the intelligence pipeline for this company.\n\nThe granular view: one entry per step with its own status, progress and\nerror. `intelligence-status` is the single rolled-up answer.","operationId":"get_company_intelligence_steps_companies__company_id__intelligence_steps_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/intelligence-status":{"get":{"tags":["Companies"],"summary":"Get Company Intelligence Status","description":"One rolled-up status for this company's intelligence run.","operationId":"get_company_intelligence_status_companies__company_id__intelligence_status_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/dashboard":{"get":{"tags":["Companies"],"summary":"Get Company Dashboard","description":"Everything the company detail view shows, in one call.\n\nThe deal it surfaces is filtered by its own ALWAYS-ENFORCED deal scope:\nbeing able to see a company never implies being able to see its deals, so\na key without deal visibility gets the dashboard with no active deal\nrather than a deal it should not see.\n\nOpen-shaped, and it has three legitimate shapes - a full dashboard, and\ntwo shells for companies that have not been through the account pipeline.\nRead `document_status` to tell them apart.","operationId":"get_company_dashboard_companies__company_id__dashboard_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/engagement-summary":{"get":{"tags":["Companies"],"summary":"Get Company Engagement Summary","description":"How much this company has engaged: emails, calls, meetings, visits.","operationId":"get_company_engagement_summary_companies__company_id__engagement_summary_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/sites-visited":{"get":{"tags":["Companies"],"summary":"Get Company Sites Visited","description":"Pages people at this company visited on your site.","operationId":"get_company_sites_visited_companies__company_id__sites_visited_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"Company business key.","title":"Company Id"},"description":"Company business key."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":730,"minimum":1,"description":"Lookback window. Bounded here rather than left open: the query is an unindexed analytics scan and an unbounded window is a cheap way to exhaust it.","default":90,"title":"Days"},"description":"Lookback window. Bounded here rather than left open: the query is an unindexed analytics scan and an unbounded window is a cheap way to exhaust it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/icp-fit":{"get":{"tags":["Companies"],"summary":"Get Company Icp Fit","description":"How well this company matches your ideal-customer profiles.\n\nA company with no match is a 404 here. The app handler answers 200 with an\n`error` key instead, which makes a missing company indistinguishable from\na scored one at the status line - translated at this boundary rather than\npublished.","operationId":"get_company_icp_fit_companies__company_id__icp_fit_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"Company business key.","title":"Company Id"},"description":"Company business key."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/next-best-step":{"get":{"tags":["Companies"],"summary":"Get Company Next Best Step","description":"What to do next with this company, and why. SPENDS CREDITS.\n\nA GET that costs money: the recommendation is generated by a model on a\ncache miss, and the cache key includes the company's engagement state, so\nactivity on the account invalidates it. Tiered `billable` for that reason\nrather than as an ordinary read.","operationId":"get_company_next_best_step_companies__company_id__next_best_step_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/companies/{company_id}/enrich":{"post":{"tags":["Companies"],"summary":"Enrich Company","description":"Look this company up with the enrichment provider. SPENDS CREDITS.\n\nQueues the lookup and returns immediately; the fields land on the company\nwhen it completes. A company with no domain is refused - the lookup is by\ndomain.\n\nThe app spells this route after the provider it happens to use today. That\nname is not published here: which provider runs is an implementation\ndetail, and the route would have to be renamed the day it changes.","operationId":"enrich_company_companies__company_id__enrich_post","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/companies/{company_id}/retry-intelligence":{"post":{"tags":["Companies"],"summary":"Retry Company Intelligence","description":"Re-run the intelligence pipeline for this company. SPENDS CREDITS.\n\nA site crawl plus several model calls per document. Omitting `doc_types`\nregenerates the DEFAULT set, so an empty body is the expensive option and\nnot the cheap one - name the documents you actually need.\n\nA run stuck for more than half an hour is treated as abandoned and\nrestarted, so this is callable again rather than wedged, but that also\nmeans it can be re-triggered on a cadence. It is tiered `billable`.","operationId":"retry_company_intelligence_companies__company_id__retry_intelligence_post","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/IntelligenceRetryRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/companies/{company_id}/retry-synthesis":{"post":{"tags":["Companies"],"summary":"Retry Company Synthesis","description":"Re-run synthesis for this company. SPENDS CREDITS.\n\nCheck `synthesis-readiness` first: a run that is missing its inputs spends\nthe same credits to produce nothing. A synthesis already marked running is\nrefused with a 409 - unlike the intelligence retry beside it there is no\nstale-run reset, so a genuinely stuck run needs support rather than a\nretry loop.","operationId":"retry_company_synthesis_companies__company_id__retry_synthesis_post","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/companies/{company_id}/documents/from-skill":{"post":{"tags":["Companies"],"summary":"Save Skill Result To Company","description":"Store a skill run's output on this company as a document.","operationId":"save_skill_result_to_company_companies__company_id__documents_from_skill_post","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SaveSkillResultRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/companies/{company_id}/linkedin-company-id":{"get":{"tags":["Companies"],"summary":"Get Company Linkedin Company Id","description":"Resolve a company's `linkedin_company_id` on demand.\n\nSplit from the company detail read because the lookup is slow. Returns\n`{linkedin_company_id, lcid_match_via}`, both `null` when unresolved.\nThe id namespace is fixed to the primary key / UUID resolver (`auto`), and\nthe access gate resolves the same namespace, so a caller cannot steer the\ngate and the handler onto different companies. Read-only; no credits.","operationId":"get_company_linkedin_company_id_companies__company_id__linkedin_company_id_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/merged-into":{"get":{"tags":["Companies"],"summary":"Get Company Merged Into","description":"Which company a merged-away company now lives in.\n\nReturns `{survivor_id, survivor_name}`. A merged-away company 404s on its\nown read; this tells you where to look instead. Returns 404 when the\ncompany was never merged, or when the key cannot see the surviving\ncompany (the survivor is access-checked, so this never reveals a record\noutside the key's visibility). Read-only.","operationId":"get_company_merged_into_companies__company_id__merged_into_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"Company primary key of a company that was merged away.","title":"Company Id"},"description":"Company primary key of a company that was merged away."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/tasks/replies/{reply_id}":{"put":{"tags":["Tasks"],"summary":"Update Task Reply","description":"Edit a reply. AUTHOR ONLY.\n\nAn organisation key has no member identity, so it is not the author of\nanything a human wrote and cannot edit those replies - it can edit the\nones it posted itself.","operationId":"update_task_reply_tasks_replies__reply_id__put","parameters":[{"name":"reply_id","in":"path","required":true,"schema":{"type":"string","description":"Reply id (UUID).","title":"Reply Id"},"description":"Reply id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TaskReplyUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"tasks:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Tasks"],"summary":"Delete Task Reply","description":"Delete a reply. AUTHOR ONLY. The rest of the thread stays.","operationId":"delete_task_reply_tasks_replies__reply_id__delete","parameters":[{"name":"reply_id","in":"path","required":true,"schema":{"type":"string","description":"Reply id (UUID).","title":"Reply Id"},"description":"Reply id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"tasks:delete","x-graph8-lifecycle":"active"}},"/tasks/{task_id}/subtasks":{"get":{"tags":["Tasks"],"summary":"List Subtasks","description":"The subtasks under one task, filtered by what this key can see.\n\nA private subtask belonging to someone else is absent rather than\nredacted, so a short list is not evidence there are no more.","operationId":"list_subtasks_tasks__task_id__subtasks_get","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Parent task id (UUID).","title":"Task Id"},"description":"Parent task id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"tasks:read","x-graph8-lifecycle":"active"},"post":{"tags":["Tasks"],"summary":"Create Subtask","description":"Create a subtask under this task.\n\n`entity_type` / `entity_id` name the RECORD the subtask hangs off and are\nrequired - the parent supplies the hierarchy, not the record link. That\nrecord is authorised against the caller's contact, company and deal\nscopes, so a subtask cannot be attached to something the key cannot see.\n\n`parent_task_id` in the body is ignored: the parent is the task in the\npath.","operationId":"create_subtask_tasks__task_id__subtasks_post","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Parent task id (UUID).","title":"Task Id"},"description":"Parent task id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SubtaskCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"tasks:write","x-graph8-lifecycle":"active"}},"/tasks/{task_id}/subtasks/{subtask_id}":{"put":{"tags":["Tasks"],"summary":"Update Subtask","description":"Patch a subtask. Omitted fields are left alone.\n\nTwo exceptions worth knowing. An explicit `null` on `due_date`,\n`assignee_id` or `task_type` CLEARS that field, which is different from\nomitting it. And `records: []` clears every record link, while omitting\n`records` leaves them unchanged.\n\n`expected_updated_at` makes the update conditional: if the stored row has\nmoved on, the write is refused instead of overwriting someone else's edit.","operationId":"update_subtask_tasks__task_id__subtasks__subtask_id__put","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Parent task id (UUID).","title":"Task Id"},"description":"Parent task id (UUID)."},{"name":"subtask_id","in":"path","required":true,"schema":{"type":"string","description":"Subtask id (UUID).","title":"Subtask Id"},"description":"Subtask id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SubtaskUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"tasks:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Tasks"],"summary":"Delete Subtask","description":"Delete one subtask. The parent and its siblings are untouched.","operationId":"delete_subtask_tasks__task_id__subtasks__subtask_id__delete","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Parent task id (UUID).","title":"Task Id"},"description":"Parent task id (UUID)."},{"name":"subtask_id","in":"path","required":true,"schema":{"type":"string","description":"Subtask id (UUID).","title":"Subtask Id"},"description":"Subtask id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"tasks:delete","x-graph8-lifecycle":"active"}},"/tasks/{task_id}/snooze":{"post":{"tags":["Tasks"],"summary":"Snooze Task Reminder","description":"Push this task's reminder out by N minutes FROM NOW.\n\nRelative to the call, not to the existing reminder time, so snoozing an\noverdue reminder by 30 moves it to half an hour from now rather than to\nhalf an hour after a moment that has passed.","operationId":"snooze_task_reminder_tasks__task_id__snooze_post","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Task id (UUID).","title":"Task Id"},"description":"Task id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SnoozeTaskRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"tasks:write","x-graph8-lifecycle":"active"}},"/tasks/{task_id}/replies":{"get":{"tags":["Tasks"],"summary":"List Task Replies","description":"The thread under a task, plus its resolution row if it has one.","operationId":"list_task_replies_tasks__task_id__replies_get","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Task id (UUID).","title":"Task Id"},"description":"Task id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"tasks:read","x-graph8-lifecycle":"active"},"post":{"tags":["Tasks"],"summary":"Create Task Reply","description":"Post a reply on this task's thread. INTERNAL to your organisation.\n\nNothing here reaches a customer. `mentioned_user_ids` notifies those\npeople inside graph8 - it does not email anyone outside it.","operationId":"create_task_reply_tasks__task_id__replies_post","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Task id (UUID).","title":"Task Id"},"description":"Task id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TaskReplyCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"tasks:write","x-graph8-lifecycle":"active"}},"/tasks/{task_id}/resolve":{"post":{"tags":["Tasks"],"summary":"Resolve Task Thread","description":"Mark this task's DISCUSSION resolved.\n\nNot the same as completing the task: a task can be done with an open\nthread, and a thread can be resolved while the task is still open.\nIdempotent - re-resolving returns the existing row rather than a second\none.","operationId":"resolve_task_thread_tasks__task_id__resolve_post","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Task id (UUID).","title":"Task Id"},"description":"Task id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ResolveThreadRequest","default":{}}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"tasks:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Tasks"],"summary":"Reopen Task Thread","description":"Reopen this task's discussion. The replies were never deleted.\n\nSpelled as a DELETE because what it removes is the RESOLUTION, not the\nthread - this is the app's own spelling and the inverse of the POST above.","operationId":"reopen_task_thread_tasks__task_id__resolve_delete","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Task id (UUID).","title":"Task Id"},"description":"Task id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"tasks:delete","x-graph8-lifecycle":"active"}},"/tasks/settings":{"get":{"tags":["Tasks"],"summary":"Get Task Settings","description":"The org's task settings: default visibility, mentions, and how a parent\ntask completes relative to its subtasks.","operationId":"get_task_settings_tasks_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"tasks:read","x-graph8-lifecycle":"active"},"put":{"tags":["Tasks"],"summary":"Update Task Settings","description":"Change how a parent task completes. ORG ADMIN ONLY.\n\nThe app gates this twice - `require_admin_access` on the route and an\nowner/admin role check in the body. The route gate is re-declared here;\nthe body check reads the role off the principal `build_api_principal`\nresolves from the validated key, so a machine key (no human, no role) is\nrefused exactly as the app would refuse a member.","operationId":"update_task_settings_tasks_settings_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TaskCompletionSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"tasks:write","x-graph8-lifecycle":"active"}},"/tasks/records/{entity_type}/{entity_id}":{"get":{"tags":["Tasks"],"summary":"Get Task Record","description":"Resolve the record a task points at to its display name and link.\n\n404 when the record does not exist or the key cannot see it. The task\nscope resolved for an API key carries no `record_scopes`, so the key's\nown resource grants (`get_task_record_scopes`, the same resolver\n`GET /tasks/{task_id}` uses) are attached before the lookup.","operationId":"get_task_record_tasks_records__entity_type___entity_id__get","parameters":[{"name":"entity_type","in":"path","required":true,"schema":{"type":"string","description":"Record type, e.g. `contact`, `company`, `deal`.","title":"Entity Type"},"description":"Record type, e.g. `contact`, `company`, `deal`."},{"name":"entity_id","in":"path","required":true,"schema":{"type":"string","description":"Record id.","title":"Entity Id"},"description":"Record id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"tasks:read","x-graph8-lifecycle":"active"}},"/notes/replies/{reply_id}":{"put":{"tags":["Notes"],"summary":"Update Note Reply","description":"Edit a reply. AUTHOR ONLY.\n\nAn organisation key has no member identity, so it is not the author of\nanything a human wrote - it can edit the replies it posted itself.","operationId":"update_note_reply_notes_replies__reply_id__put","parameters":[{"name":"reply_id","in":"path","required":true,"schema":{"type":"string","description":"Reply id (UUID).","title":"Reply Id"},"description":"Reply id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NoteReplyUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"notes:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Notes"],"summary":"Delete Note Reply","description":"Delete a reply. AUTHOR ONLY. The rest of the thread stays.","operationId":"delete_note_reply_notes_replies__reply_id__delete","parameters":[{"name":"reply_id","in":"path","required":true,"schema":{"type":"string","description":"Reply id (UUID).","title":"Reply Id"},"description":"Reply id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"notes:delete","x-graph8-lifecycle":"active"}},"/notes/{note_id}/replies":{"get":{"tags":["Notes"],"summary":"List Note Replies","description":"The thread under a note, plus its resolution row if it has one.","operationId":"list_note_replies_notes__note_id__replies_get","parameters":[{"name":"note_id","in":"path","required":true,"schema":{"type":"string","description":"Note id (UUID).","title":"Note Id"},"description":"Note id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"notes:read","x-graph8-lifecycle":"active"},"post":{"tags":["Notes"],"summary":"Create Note Reply","description":"Post a reply on this note's thread. INTERNAL to your organisation.\n\nNothing here reaches the contact the note is about. `mentioned_user_ids`\nnotifies those people inside graph8.\n\nWrite access is checked against the RECORD the note hangs off, not the\nnote: replying is a write to that record's collaboration surface.","operationId":"create_note_reply_notes__note_id__replies_post","parameters":[{"name":"note_id","in":"path","required":true,"schema":{"type":"string","description":"Note id (UUID).","title":"Note Id"},"description":"Note id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NoteReplyCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"notes:write","x-graph8-lifecycle":"active"}},"/notes/{note_id}/resolve":{"post":{"tags":["Notes"],"summary":"Resolve Note Thread","description":"Mark this note's discussion resolved.\n\nIdempotent - re-resolving returns the existing row rather than creating a\nsecond one. The replies are untouched.","operationId":"resolve_note_thread_notes__note_id__resolve_post","parameters":[{"name":"note_id","in":"path","required":true,"schema":{"type":"string","description":"Note id (UUID).","title":"Note Id"},"description":"Note id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ResolveThreadRequest","default":{}}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"notes:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Notes"],"summary":"Reopen Note Thread","description":"Reopen this note's discussion. Nothing is deleted.\n\nSpelled as a DELETE because what it removes is the RESOLUTION, not the\nthread - the app's own spelling, and the inverse of the POST above. It is\na WRITE on the underlying record despite the verb, and the gate says so\nexplicitly rather than inferring it from the method.","operationId":"reopen_note_thread_notes__note_id__resolve_delete","parameters":[{"name":"note_id","in":"path","required":true,"schema":{"type":"string","description":"Note id (UUID).","title":"Note Id"},"description":"Note id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"notes:delete","x-graph8-lifecycle":"active"}},"/notes":{"get":{"tags":["Notes"],"summary":"List Notes For Record","description":"Every note on one record, including notes that only MENTION it.\n\nThe per-record reads (`GET /contacts/{id}/notes` and friends) return the\nnotes attached to the record; this one also follows secondary links, so a\nnote filed on a deal that names this contact appears here too.","operationId":"list_notes_for_record_notes_get","parameters":[{"name":"entity_type","in":"query","required":true,"schema":{"type":"string","description":"Record type, e.g. `contact`, `company`, `deal`.","title":"Entity Type"},"description":"Record type, e.g. `contact`, `company`, `deal`."},{"name":"entity_id","in":"query","required":true,"schema":{"type":"string","description":"Id of that record.","title":"Entity Id"},"description":"Id of that record."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"notes:read","x-graph8-lifecycle":"active"},"post":{"tags":["Notes"],"summary":"Create Record Note","description":"Create a note attached to one or MORE records.\n\nWith `records`, the first entry is the primary record and every entry is\nlinked; without it, `entity_type`/`entity_id` name the single record.\nEvery record is authorised for write before anything is stored.","operationId":"create_record_note_notes_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RecordNoteCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"notes:write","x-graph8-lifecycle":"active"}},"/notes/batch":{"post":{"tags":["Notes"],"summary":"List Notes For Contacts","description":"The notes of many contacts in one read, grouped by contact. Writes nothing.\n\nPOST only because the id list is a body. Every contact is authorised first.","operationId":"list_notes_for_contacts_notes_batch_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NoteBatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"notes:read","x-graph8-lifecycle":"active"}},"/notes/{note_id}/records":{"post":{"tags":["Notes"],"summary":"Link Note Record","description":"Also file this note under another record. Idempotent.","operationId":"link_note_record_notes__note_id__records_post","parameters":[{"name":"note_id","in":"path","required":true,"schema":{"type":"string","description":"Note id (UUID).","title":"Note Id"},"description":"Note id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NoteRecordLinkRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"notes:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Notes"],"summary":"Unlink Note Record","description":"Stop filing this note under a record. The note itself is kept.\n\nThe app takes the record in a DELETE body; it is a query string here,\nbecause a body on DELETE is dropped by many HTTP clients and proxies.\nThe app refuses to remove a note's LAST record, so a note never orphans.","operationId":"unlink_note_record_notes__note_id__records_delete","parameters":[{"name":"note_id","in":"path","required":true,"schema":{"type":"string","description":"Note id (UUID).","title":"Note Id"},"description":"Note id (UUID)."},{"name":"entity_type","in":"query","required":true,"schema":{"type":"string","description":"Record type to unlink.","title":"Entity Type"},"description":"Record type to unlink."},{"name":"entity_id","in":"query","required":true,"schema":{"type":"string","description":"Record id to unlink.","title":"Entity Id"},"description":"Record id to unlink."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"notes:delete","x-graph8-lifecycle":"active"}},"/notifications/by-entity/read":{"put":{"tags":["Notifications"],"summary":"Mark Notifications By Entity Read","description":"Mark the whole team's notifications for one record as READ.\n\nThe rows survive, stamped with who read them, so the bell can still show\nthat someone acknowledged it. Idempotent: only unread rows are touched.\n\nOmitting `notification_type` is the wide option - it marks every\nnotification anyone in the org holds for that record, including mentions\nthat were meant for a person.","operationId":"mark_notifications_by_entity_read_notifications_by_entity_read_put","parameters":[{"name":"entity_type","in":"query","required":true,"schema":{"type":"string","description":"Record type the notification is about, e.g. `chat`.","title":"Entity Type"},"description":"Record type the notification is about, e.g. `chat`."},{"name":"entity_id","in":"query","required":true,"schema":{"type":"string","description":"Id of that record.","title":"Entity Id"},"description":"Id of that record."},{"name":"notification_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to one notification type. Pass the type you own - omitting it also marks unrelated notifications on the same record, such as a colleague's mention.","title":"Notification Type"},"description":"Narrow to one notification type. Pass the type you own - omitting it also marks unrelated notifications on the same record, such as a colleague's mention."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/notifications/by-entity":{"delete":{"tags":["Notifications"],"summary":"Delete Notifications By Entity","description":"Delete the whole team's notifications for one record.\n\nRemoves the rows for every user in your organisation, not just the\ncaller's. There is no undo, and unlike the read marker above nothing\nsurvives to show the notification existed - prefer\n`PUT /notifications/by-entity/read` unless the notification was noise.","operationId":"delete_notifications_by_entity_notifications_by_entity_delete","parameters":[{"name":"entity_type","in":"query","required":true,"schema":{"type":"string","description":"Record type the notification is about, e.g. `chat`.","title":"Entity Type"},"description":"Record type the notification is about, e.g. `chat`."},{"name":"entity_id","in":"query","required":true,"schema":{"type":"string","description":"Id of that record.","title":"Entity Id"},"description":"Id of that record."},{"name":"notification_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to one notification type. Pass the type you own - omitting it also deletes unrelated notifications on the same record.","title":"Notification Type"},"description":"Narrow to one notification type. Pass the type you own - omitting it also deletes unrelated notifications on the same record."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/company-profile/workflow-status":{"get":{"tags":["GTM Context"],"summary":"Get Company Profile Workflow Status","description":"How far the profile-building pipeline has got, card by card.\n\nFour stages - intelligence gathering, the merge, approval, and the profile\nitself - each with its own state, so a caller can tell \"still crawling\"\nfrom \"waiting for a human\" from \"done\".\n\nThe `website_url` echoed back is the string you sent; the lookup itself is\ndone against its canonical domain, so a match on a differently-spelled URL\nis expected rather than a mismatch.","operationId":"get_company_profile_workflow_status_company_profile_workflow_status_get","parameters":[{"name":"website_url","in":"query","required":true,"schema":{"type":"string","description":"The website the profile was built from.","title":"Website Url"},"description":"The website the profile was built from."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/company-profile/unapprove":{"post":{"tags":["GTM Context"],"summary":"Unapprove Company Profile","description":"Release a human's approval on the profile so it can be rewritten.\n\nAn approved profile is immutable through `PUT /company-profile` unless\nthat call is sent with `unapprove_if_approved`. This is the standalone\nhalf: it clears the approval WITHOUT changing a field, which is what you\nwant when the approval was premature rather than the content wrong.\n\nOrg-wide and immediate. Nothing re-approves automatically.","operationId":"unapprove_company_profile_company_profile_unapprove_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProfileWebsiteRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/company-profile/reindex":{"post":{"tags":["GTM Context"],"summary":"Reindex Company Profile","description":"Rebuild the search index over this profile. SPENDS PROVIDER BUDGET.\n\nEvery call re-embeds the whole profile through the embedding provider -\nthere is no dedupe, and the cost is proportional to how much is in the\nprofile rather than to what changed. Tiered `billable` for that reason.\n\nWorth calling after a profile edit: the published `PUT /company-profile`\nwrites the row but does NOT re-index, so anything that reads the profile\nthrough search stays stale until this runs.\n\nThe website is taken in the BODY here. The app reads it as a query\nparameter on a POST, which is the kind of detail that only bites once.","operationId":"reindex_company_profile_company_profile_reindex_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProfileWebsiteRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/company-profile/keywords":{"delete":{"tags":["GTM Context"],"summary":"Reset Company Profile Keywords","description":"Delete the keywords derived for this profile. NOT REVERSIBLE.\n\nA hard delete with no soft-delete row behind it: the keywords are gone and\nthe only way back is to regenerate them. Returns how many were removed.","operationId":"reset_company_profile_keywords_company_profile_keywords_delete","parameters":[{"name":"website_url","in":"query","required":true,"schema":{"type":"string","description":"The website the profile was built from.","title":"Website Url"},"description":"The website the profile was built from."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/company-profile/approve":{"post":{"tags":["GTM Context"],"summary":"Approve Company Profile","description":"Approve the profile. It becomes the org's source of truth and is locked.\n\nRefused until the first generation run has completed. Undo with\n`POST /company-profile/unapprove`.","operationId":"approve_company_profile_company_profile_approve_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProfileWebsiteRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/company-profile/keywords/approve":{"post":{"tags":["GTM Context"],"summary":"Approve Company Profile Keywords","description":"Approve the profile's keyword set. 404 until a profile with keywords exists.","operationId":"approve_company_profile_keywords_company_profile_keywords_approve_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProfileWebsiteRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/company-profile/generate":{"post":{"tags":["GTM Context"],"summary":"Generate Company Profile","description":"(Re)build the profile's company data from the crawled site. SPENDS CREDITS.\n\nModel calls plus a web-search enrichment; refused with 402 before any\ncall when the org is out of credits. REPLACES the unapproved profile data.","operationId":"generate_company_profile_company_profile_generate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProfileFieldsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/company-profile/retry":{"post":{"tags":["GTM Context"],"summary":"Retry Company Profile","description":"Delete the profile and generate it again from intelligence. SPENDS CREDITS.","operationId":"retry_company_profile_company_profile_retry_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProfileWebsiteRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/company-profile/logo":{"post":{"tags":["GTM Context"],"summary":"Upload Company Profile Logo","description":"Upload the org's logo and set it on the profile. Multipart.\n\nThe public booking page shows this logo.","operationId":"upload_company_profile_logo_company_profile_logo_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_company_profile_logo_company_profile_logo_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/security-questionnaires":{"post":{"tags":["Documents"],"summary":"Upload Security Questionnaire","description":"Upload a questionnaire and start answering it. ASYNCHRONOUS.\n\nAnswering runs in the background against the org's answer library and\npolicy documents, so this returns as soon as the file is accepted. Poll\n`/security-questionnaires/{id}/status` for progress and\n`/security-questionnaires/{id}` for the questions as they land.\n\nMultipart, like the app.","operationId":"upload_security_questionnaire_accounts__account_id__security_questionnaires_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account the questionnaire came from.","title":"Account Id"},"description":"The account the questionnaire came from."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_security_questionnaire_accounts__account_id__security_questionnaires_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"knowledge:run","x-graph8-lifecycle":"active"},"get":{"tags":["Documents"],"summary":"List Security Questionnaires","description":"Every questionnaire for this account.","operationId":"list_security_questionnaires_accounts__account_id__security_questionnaires_get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account.","title":"Account Id"},"description":"The account."},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only questionnaires in this state: `processing`, `completed`, `needs_review` or `failed`. Omit for all.","title":"Status"},"description":"Only questionnaires in this state: `processing`, `completed`, `needs_review` or `failed`. Omit for all."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/security-questionnaires/{questionnaire_id}":{"get":{"tags":["Documents"],"summary":"Get Security Questionnaire","description":"One questionnaire, with every question and its answer.\n\nThe read the review loop is built on: each question carries the AI's\nanswer, the human's edit if there is one, the confidence, and whether it\nhas been approved, escalated, skipped or marked wrong.","operationId":"get_security_questionnaire_accounts__account_id__security_questionnaires__questionnaire_id__get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account.","title":"Account Id"},"description":"The account."},{"name":"questionnaire_id","in":"path","required":true,"schema":{"type":"string","description":"Questionnaire id (UUID).","title":"Questionnaire Id"},"description":"Questionnaire id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Documents"],"summary":"Update Security Questionnaire","description":"Rename a questionnaire. Metadata only - it never touches an answer.","operationId":"update_security_questionnaire_accounts__account_id__security_questionnaires__questionnaire_id__patch","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account.","title":"Account Id"},"description":"The account."},{"name":"questionnaire_id","in":"path","required":true,"schema":{"type":"string","description":"Questionnaire id (UUID).","title":"Questionnaire Id"},"description":"Questionnaire id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuestionnaireUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Documents"],"summary":"Delete Security Questionnaire","description":"Delete a questionnaire AND every question on it. Not reversible.\n\n204 with no body, matching the app - there is nothing left to describe.","operationId":"delete_security_questionnaire_accounts__account_id__security_questionnaires__questionnaire_id__delete","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account.","title":"Account Id"},"description":"The account."},{"name":"questionnaire_id","in":"path","required":true,"schema":{"type":"string","description":"Questionnaire id (UUID).","title":"Questionnaire Id"},"description":"Questionnaire id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"companies:delete","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/security-questionnaires/{questionnaire_id}/status":{"get":{"tags":["Documents"],"summary":"Get Security Questionnaire Status","description":"Progress only - the cheap read to POLL.\n\nThe full detail read returns every question and grows with the document;\nthis one answers \"is it done yet\" without transferring it.","operationId":"get_security_questionnaire_status_accounts__account_id__security_questionnaires__questionnaire_id__status_get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account.","title":"Account Id"},"description":"The account."},{"name":"questionnaire_id","in":"path","required":true,"schema":{"type":"string","description":"Questionnaire id (UUID).","title":"Questionnaire Id"},"description":"Questionnaire id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/security-questionnaires/{questionnaire_id}/download":{"get":{"tags":["Documents"],"summary":"Download Security Questionnaire","description":"The FILLED workbook, as XLSX bytes.\n\nNot the `ApiResponse` envelope - a spreadsheet wrapped in JSON is not a\nspreadsheet. Same precedent as `GET /knowledge/export`.\n\nOnly available once the questionnaire is `completed` or `needs_review`;\nasking earlier is refused rather than returning a half-filled file.","operationId":"download_security_questionnaire_accounts__account_id__security_questionnaires__questionnaire_id__download_get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account.","title":"Account Id"},"description":"The account."},{"name":"questionnaire_id","in":"path","required":true,"schema":{"type":"string","description":"Questionnaire id (UUID).","title":"Questionnaire Id"},"description":"Questionnaire id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/security-questionnaires/{questionnaire_id}/questions/{question_id}":{"patch":{"tags":["Documents"],"summary":"Update Questionnaire Answer","description":"Replace one answer with a human-written one.\n\nThe edit lands in `final_answer` and is what the downloaded workbook\ncarries. The model's original answer is KEPT alongside it, so the two can\nstill be compared afterwards.","operationId":"update_questionnaire_answer_accounts__account_id__security_questionnaires__questionnaire_id__questions__question_id__patch","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account.","title":"Account Id"},"description":"The account."},{"name":"questionnaire_id","in":"path","required":true,"schema":{"type":"string","description":"Questionnaire id (UUID).","title":"Questionnaire Id"},"description":"Questionnaire id (UUID)."},{"name":"question_id","in":"path","required":true,"schema":{"type":"string","description":"Question id (UUID), from the questionnaire detail read.","title":"Question Id"},"description":"Question id (UUID), from the questionnaire detail read."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuestionAnswerUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/security-questionnaires/{questionnaire_id}/questions/{question_id}/approve":{"post":{"tags":["Documents"],"summary":"Approve Questionnaire Answer","description":"Confirm an answer as correct. No body - approving is the whole message.\n\nThis is the signal that takes a questionnaire from `needs_review` towards\ndone; it changes no text.","operationId":"approve_questionnaire_answer_accounts__account_id__security_questionnaires__questionnaire_id__questions__question_id__approve_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account.","title":"Account Id"},"description":"The account."},{"name":"questionnaire_id","in":"path","required":true,"schema":{"type":"string","description":"Questionnaire id (UUID).","title":"Questionnaire Id"},"description":"Questionnaire id (UUID)."},{"name":"question_id","in":"path","required":true,"schema":{"type":"string","description":"Question id (UUID), from the questionnaire detail read.","title":"Question Id"},"description":"Question id (UUID), from the questionnaire detail read."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/security-questionnaires/{questionnaire_id}/questions/{question_id}/escalate":{"post":{"tags":["Documents"],"summary":"Escalate Questionnaire Question","description":"Hand a question to the security team.\n\nFor the questions the answer library genuinely cannot settle. `notes` is\nwhat the person picking it up reads, so it is worth sending even though\nthe app allows it to be empty.","operationId":"escalate_questionnaire_question_accounts__account_id__security_questionnaires__questionnaire_id__questions__question_id__escalate_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account.","title":"Account Id"},"description":"The account."},{"name":"questionnaire_id","in":"path","required":true,"schema":{"type":"string","description":"Questionnaire id (UUID).","title":"Questionnaire Id"},"description":"Questionnaire id (UUID)."},{"name":"question_id","in":"path","required":true,"schema":{"type":"string","description":"Question id (UUID), from the questionnaire detail read.","title":"Question Id"},"description":"Question id (UUID), from the questionnaire detail read."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuestionNoteRequest","default":{}}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/security-questionnaires/{questionnaire_id}/questions/{question_id}/mark-skip":{"post":{"tags":["Documents"],"summary":"Skip Questionnaire Question","description":"Mark a question as NOT APPLICABLE to this organisation.\n\nDifferent from escalating: nobody is going to answer this one, and the\nfilled workbook says so rather than leaving it blank.","operationId":"skip_questionnaire_question_accounts__account_id__security_questionnaires__questionnaire_id__questions__question_id__mark_skip_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account.","title":"Account Id"},"description":"The account."},{"name":"questionnaire_id","in":"path","required":true,"schema":{"type":"string","description":"Questionnaire id (UUID).","title":"Questionnaire Id"},"description":"Questionnaire id (UUID)."},{"name":"question_id","in":"path","required":true,"schema":{"type":"string","description":"Question id (UUID), from the questionnaire detail read.","title":"Question Id"},"description":"Question id (UUID), from the questionnaire detail read."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuestionNoteRequest","default":{}}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/security-questionnaires/{questionnaire_id}/questions/{question_id}/mark-wrong":{"post":{"tags":["Documents"],"summary":"Flag Questionnaire Answer","description":"Say the AI's answer is WRONG and needs replacing.\n\nThe feedback signal, not a fix: it flags the answer for a human to\nrewrite with `PATCH .../questions/{question_id}`.","operationId":"flag_questionnaire_answer_accounts__account_id__security_questionnaires__questionnaire_id__questions__question_id__mark_wrong_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account.","title":"Account Id"},"description":"The account."},{"name":"questionnaire_id","in":"path","required":true,"schema":{"type":"string","description":"Questionnaire id (UUID).","title":"Questionnaire Id"},"description":"Questionnaire id (UUID)."},{"name":"question_id","in":"path","required":true,"schema":{"type":"string","description":"Question id (UUID), from the questionnaire detail read.","title":"Question Id"},"description":"Question id (UUID), from the questionnaire detail read."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuestionNoteRequest","default":{}}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/security-questionnaires/{questionnaire_id}/questions/{question_id}/save-to-library":{"post":{"tags":["Documents"],"summary":"Save Questionnaire Answer To Library","description":"Promote this answer into the reusable answer library.\n\nThe compounding step: an answer saved here is what the NEXT questionnaire\nis answered from, so a reviewed answer stops being a one-off edit and\nstarts being org knowledge.","operationId":"save_questionnaire_answer_to_library_accounts__account_id__security_questionnaires__questionnaire_id__questions__question_id__save_to_library_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account.","title":"Account Id"},"description":"The account."},{"name":"questionnaire_id","in":"path","required":true,"schema":{"type":"string","description":"Questionnaire id (UUID).","title":"Questionnaire Id"},"description":"Questionnaire id (UUID)."},{"name":"question_id","in":"path","required":true,"schema":{"type":"string","description":"Question id (UUID), from the questionnaire detail read.","title":"Question Id"},"description":"Question id (UUID), from the questionnaire detail read."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/correspondence":{"get":{"tags":["Documents"],"summary":"List Account Correspondence","description":"What has been said to this account, across channels.","operationId":"list_account_correspondence_accounts__account_id__correspondence_get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account.","title":"Account Id"},"description":"The account."},{"name":"channel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"`email`, `linkedin` or `call_notes`. Omit for all.","title":"Channel"},"description":"`email`, `linkedin` or `call_notes`. Omit for all."},{"name":"stakeholder_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only what was said to or by this person.","title":"Stakeholder Id"},"description":"Only what was said to or by this person."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"},"post":{"tags":["Documents"],"summary":"Create Account Correspondence","description":"Record ONE message, call or note against an account.\n\n`correspondence_date` is when it HAPPENED, not when it was recorded - the\ngenerated documents read it as the relationship's timeline, so a wrong\ndate is worse than a missing record.","operationId":"create_account_correspondence_accounts__account_id__correspondence_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account.","title":"Account Id"},"description":"The account."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CorrespondenceCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/correspondence/import":{"post":{"tags":["Documents"],"summary":"Import Account Correspondence","description":"Import a batch of correspondence. PARTIAL SUCCESS IS NORMAL.\n\nThe response reports `imported`, `skipped` and `errors` and the status\nstays 200 even when rows failed - read the body, not the status. Send\n`external_id` on each item to make the import re-runnable: a row whose\n`external_id` is already stored is SKIPPED rather than duplicated.","operationId":"import_account_correspondence_accounts__account_id__correspondence_import_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account.","title":"Account Id"},"description":"The account."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CorrespondenceImportRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/correspondence/upload":{"post":{"tags":["Documents"],"summary":"Upload Account Correspondence","description":"Record correspondence from a FILE rather than a JSON body.\n\nThe route for a forwarded `.eml` or an exported thread: the file's text\nbecomes the content, and the record is created in the same call.\n\nThis handler is `async def` but takes the SYNC session, so it is awaited\ndirectly rather than going through the threadpool helper.","operationId":"upload_account_correspondence_accounts__account_id__correspondence_upload_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account.","title":"Account Id"},"description":"The account."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_account_correspondence_accounts__account_id__correspondence_upload_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/correspondence/{correspondence_id}":{"delete":{"tags":["Documents"],"summary":"Delete Account Correspondence","description":"Delete one correspondence record. 204, matching the app.\n\nThe generated documents that already cited it are not rewritten - this\nremoves the source, not its consequences.","operationId":"delete_account_correspondence_accounts__account_id__correspondence__correspondence_id__delete","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"The account.","title":"Account Id"},"description":"The account."},{"name":"correspondence_id","in":"path","required":true,"schema":{"type":"string","description":"The record to remove.","title":"Correspondence Id"},"description":"The record to remove."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"companies:delete","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/documents/generate-all":{"post":{"tags":["Deals"],"summary":"Generate All Deal Documents","description":"Generate all six documents for this deal. SPENDS CREDITS.\n\nASYNCHRONOUS: the work is queued and this returns straight away. Poll\n`/documents/generation-status`.\n\nThe app REFUSES this when the deal's company has no completed synthesis\ndocuments of its own - the deal documents are written from them, so\nwithout them there is nothing to write from. Generate the company\ndocuments first.","operationId":"generate_all_deal_documents_deals__deal_id__documents_generate_all_post","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/documents/generation-status":{"get":{"tags":["Deals"],"summary":"Get Deal Document Generation Status","description":"How the generation is going - the cheap read to POLL.\n\nCounts rather than content: total, ready, generating, failed. Listing the\ndocuments transfers every body, which is the wrong call in a poll loop.","operationId":"get_deal_document_generation_status_deals__deal_id__documents_generation_status_get","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/documents/types/{doc_type}":{"get":{"tags":["Deals"],"summary":"Get Deal Document","description":"One generated document, in full.\n\nThere is at most ONE document per type per deal, which is why the type\nidentifies it. 404 when it has not been generated yet.","operationId":"get_deal_document_deals__deal_id__documents_types__doc_type__get","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"doc_type","in":"path","required":true,"schema":{"enum":["deal_risks","next_steps","close_plan","scope_of_work","roi_analysis","competitive_analysis"],"type":"string","description":"Which generated document. One of the six the deal synthesis produces; anything else is a 422 naming them.","title":"Doc Type"},"description":"Which generated document. One of the six the deal synthesis produces; anything else is a 422 naming them."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/documents/types/{doc_type}/generate":{"post":{"tags":["Deals"],"summary":"Generate Deal Document","description":"Generate ONE document. SPENDS CREDITS.\n\nIDEMPOTENT ONLY IN THE SENSE THAT IT WILL NOT DUPLICATE: if the document\nalready exists this OVERWRITES it, and the response says so with\n`is_regeneration`. It does not skip, so a retried call is a second spend.\n\nQueued, not synchronous - poll `/documents/generation-status`.","operationId":"generate_deal_document_deals__deal_id__documents_types__doc_type__generate_post","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"doc_type","in":"path","required":true,"schema":{"enum":["deal_risks","next_steps","close_plan","scope_of_work","roi_analysis","competitive_analysis"],"type":"string","description":"Which generated document. One of the six the deal synthesis produces; anything else is a 422 naming them.","title":"Doc Type"},"description":"Which generated document. One of the six the deal synthesis produces; anything else is a 422 naming them."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/documents/types/{doc_type}/regenerate":{"post":{"tags":["Deals"],"summary":"Regenerate Deal Document","description":"Re-write a document that already exists. SPENDS CREDITS.\n\nThe difference from `/generate` is what happens when the document is\nMISSING: this 404s, `/generate` creates it. Use this when you want to be\nsure you are replacing rather than creating.","operationId":"regenerate_deal_document_deals__deal_id__documents_types__doc_type__regenerate_post","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"doc_type","in":"path","required":true,"schema":{"enum":["deal_risks","next_steps","close_plan","scope_of_work","roi_analysis","competitive_analysis"],"type":"string","description":"Which generated document. One of the six the deal synthesis produces; anything else is a 422 naming them.","title":"Doc Type"},"description":"Which generated document. One of the six the deal synthesis produces; anything else is a 422 naming them."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/documents":{"get":{"tags":["Deals"],"summary":"List Deal Documents","description":"Every generated document on this deal, newest first.\n\nCarries each document's body, so it is the wrong read for a poll loop -\nuse `/documents/generation-status` for that.","operationId":"list_deal_documents_deals__deal_id__documents_get","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"folder","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"`strategy` or `analysis`. Not validated by the app - an unrecognised folder matches nothing rather than failing.","title":"Folder"},"description":"`strategy` or `analysis`. Not validated by the app - an unrecognised folder matches nothing rather than failing."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/documents/{document_id}":{"put":{"tags":["Deals"],"summary":"Update Deal Document","description":"Edit a generated document by hand.\n\nKeyed by document ID, not by type - this is the one place the two\nidentifier spaces differ, and it is why the type-keyed routes live under\n`/documents/types/`.\n\nAn omitted field is left alone; `structured_data` REPLACES the stored\nobject rather than merging into it. A later regeneration OVERWRITES the\nedit, so edit last.","operationId":"update_deal_document_deals__deal_id__documents__document_id__put","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document id, from the list read.","title":"Document Id"},"description":"Document id, from the list read."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DealDocumentUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Deals"],"summary":"Delete Deal Document","description":"Remove a generated document.\n\nNot destructive in the way a deleted record is: the document can be\ngenerated again from the same sources - at the cost of the credits that\ntakes.","operationId":"delete_deal_document_deals__deal_id__documents__document_id__delete","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document id, from the list read.","title":"Document Id"},"description":"Document id, from the list read."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"deals:delete","x-graph8-lifecycle":"active"}},"/library/documents/upload":{"post":{"tags":["Documents"],"summary":"Upload Library Document","description":"Upload ONE file to the Library. Multipart, like the app.\n\nThe app's rules are enforced by the app and documented here so a caller\nsees them before spending the upload: 50 MB maximum, and the extension\nmust be one of pdf, docx, doc, txt, md, mdx, csv, json, png, jpg, jpeg,\nxls, xlsx, ppt, pptx. Text-bearing types are extracted and indexed for\nretrieval; the rest are stored as bytes.","operationId":"upload_library_document_library_documents_upload_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_library_document_library_documents_upload_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/library/documents/upload-batch":{"post":{"tags":["Documents"],"summary":"Upload Library Documents","description":"Upload SEVERAL files in one request.\n\nPARTIAL SUCCESS IS THE NORMAL OUTCOME. Each file is processed on its own\nsession, so one rejected file does not roll the others back and the status\nstays 201. Read the per-file result in the body, not the HTTP status.\n\nNamed `upload-batch` rather than the app's `upload-multi`: the same\noperation, spelled the way the rest of this contract spells a bulk verb.","operationId":"upload_library_documents_library_documents_upload_batch_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_library_documents_library_documents_upload_batch_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/library/documents/reextract-all":{"post":{"tags":["Documents"],"summary":"Reextract All Library Documents","description":"Re-run text extraction across a folder, or the whole library.\n\nUse it after an extraction improvement, or when documents uploaded before\na fix have empty or garbled text. It replaces the stored text; the\noriginal bytes are untouched.","operationId":"reextract_all_library_documents_library_documents_reextract_all_post","parameters":[{"name":"folder_path","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Limit to one folder. Omit to re-extract EVERY PDF and DOCX in the library, which on a large library is a long job.","title":"Folder Path"},"description":"Limit to one folder. Omit to re-extract EVERY PDF and DOCX in the library, which on a large library is a long job."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/library/documents":{"post":{"tags":["Documents"],"summary":"Create Library Document","description":"Create a TEXT document from a string.\n\nThe counterpart to `/documents/upload`: no file, no extraction, the\n`content` you send is the content stored. Use it for material you already\nhave as text.","operationId":"create_library_document_library_documents_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LibraryDocumentCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"},"get":{"tags":["Documents"],"summary":"List Library Documents","description":"What is in the library.","operationId":"list_library_documents_library_documents_get","parameters":[{"name":"context_type","in":"query","required":false,"schema":{"enum":["global","campaign","account"],"type":"string","description":"Whose library to read. `campaign` and `account` additionally need the matching id below; without it the app reads the GLOBAL library, which is a different set of documents rather than an error.","default":"global","title":"Context Type"},"description":"Whose library to read. `campaign` and `account` additionally need the matching id below; without it the app reads the GLOBAL library, which is a different set of documents rather than an error."},{"name":"campaign_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Campaign id. Only read when `context_type` is `campaign`.","title":"Campaign Id"},"description":"Campaign id. Only read when `context_type` is `campaign`."},{"name":"account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Account id. Only read when `context_type` is `account`.","title":"Account Id"},"description":"Account id. Only read when `context_type` is `account`."},{"name":"folder_path","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only this folder.","title":"Folder Path"},"description":"Only this folder."},{"name":"include_deleted","in":"query","required":false,"schema":{"type":"boolean","description":"Include soft-deleted documents, which is how you find something to pass to `/documents/{id}/restore`.","default":false,"title":"Include Deleted"},"description":"Include soft-deleted documents, which is how you find something to pass to `/documents/{id}/restore`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/library/documents/{document_id}":{"get":{"tags":["Documents"],"summary":"Get Library Document","description":"One document, with its extracted text.\n\nFor the original bytes use `/documents/{id}/download`.","operationId":"get_library_document_library_documents__document_id__get","parameters":[{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Document Id"},"description":"Document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"},"put":{"tags":["Documents"],"summary":"Update Library Document","description":"Edit a document: rename it, replace its text, or move it.\n\nPARTIAL despite the PUT verb - an omitted field is left alone, which is\nthe app's own shape. `meta_data` REPLACES the stored object rather than\nmerging into it.","operationId":"update_library_document_library_documents__document_id__put","parameters":[{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Document Id"},"description":"Document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LibraryDocumentUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Documents"],"summary":"Delete Library Document","description":"Delete a document PERMANENTLY. The row and its bytes go.\n\nThis is the app's hard delete, not the soft delete `/documents/{id}/restore`\nreverses - a document removed here cannot be restored.","operationId":"delete_library_document_library_documents__document_id__delete","parameters":[{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Document Id"},"description":"Document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"knowledge:delete","x-graph8-lifecycle":"active"}},"/library/documents/{document_id}/download":{"get":{"tags":["Documents"],"summary":"Download Library Document","description":"The document's ORIGINAL bytes, with its own content type.\n\nThe one route on this surface that is NOT the `ApiResponse` envelope: a\nPDF wrapped in JSON is not a PDF. Same precedent as\n`GET /knowledge/export`. Content type and filename come from the stored\ndocument, so a text document comes back as text and a PDF as a PDF.","operationId":"download_library_document_library_documents__document_id__download_get","parameters":[{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Document Id"},"description":"Document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/library/documents/{document_id}/reextract":{"post":{"tags":["Documents"],"summary":"Reextract Library Document","description":"Re-run text extraction on ONE PDF or DOCX.\n\nThe single-document form of `/documents/reextract-all`. The stored bytes\nare the input and are not changed.","operationId":"reextract_library_document_library_documents__document_id__reextract_post","parameters":[{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Document Id"},"description":"Document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/library/documents/{document_id}/restore":{"post":{"tags":["Documents"],"summary":"Restore Library Document","description":"Undo a SOFT delete.\n\nFind the id with `GET /library/documents?include_deleted=true`. This\ncannot bring back a document removed by `DELETE`, which is permanent.","operationId":"restore_library_document_library_documents__document_id__restore_post","parameters":[{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Document Id"},"description":"Document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/library/documents/{document_id}/refresh":{"post":{"tags":["Documents"],"summary":"Refresh Library Document","description":"Re-fetch a document that was SCRAPED from a URL.\n\nOnly meaningful for a document whose `source` is `scrape`; anything else\nis refused, because there is no URL to go back to.","operationId":"refresh_library_document_library_documents__document_id__refresh_post","parameters":[{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Document Id"},"description":"Document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/library/folders":{"post":{"tags":["Documents"],"summary":"Create Library Folder","description":"Create a folder. `parent_path` `Library` is the root.","operationId":"create_library_folder_library_folders_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LibraryFolderCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"},"get":{"tags":["Documents"],"summary":"List Library Folders","description":"The folders, flat. For the nested shape use `/library/tree`.","operationId":"list_library_folders_library_folders_get","parameters":[{"name":"context_type","in":"query","required":false,"schema":{"enum":["global","campaign","account"],"type":"string","description":"Whose library to read. `campaign` and `account` additionally need the matching id below; without it the app reads the GLOBAL library, which is a different set of documents rather than an error.","default":"global","title":"Context Type"},"description":"Whose library to read. `campaign` and `account` additionally need the matching id below; without it the app reads the GLOBAL library, which is a different set of documents rather than an error."},{"name":"campaign_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Campaign id. Only read when `context_type` is `campaign`.","title":"Campaign Id"},"description":"Campaign id. Only read when `context_type` is `campaign`."},{"name":"account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Account id. Only read when `context_type` is `account`.","title":"Account Id"},"description":"Account id. Only read when `context_type` is `account`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/library/folders/{folder_id}":{"put":{"tags":["Documents"],"summary":"Rename Library Folder","description":"Rename a folder. The documents inside keep their ids.","operationId":"rename_library_folder_library_folders__folder_id__put","parameters":[{"name":"folder_id","in":"path","required":true,"schema":{"type":"string","description":"Folder id.","title":"Folder Id"},"description":"Folder id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LibraryFolderRenameRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Documents"],"summary":"Delete Library Folder","description":"Delete a folder. It must be EMPTY - this never deletes documents.","operationId":"delete_library_folder_library_folders__folder_id__delete","parameters":[{"name":"folder_id","in":"path","required":true,"schema":{"type":"string","description":"Folder id.","title":"Folder Id"},"description":"Folder id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"knowledge:delete","x-graph8-lifecycle":"active"}},"/library/tree":{"get":{"tags":["Documents"],"summary":"Get Library Tree","description":"Folders and their documents, nested - the whole library in one call.\n\nThe read to build a file browser from. `/library/folders` and\n`/library/documents` are the flat halves of the same data.","operationId":"get_library_tree_library_tree_get","parameters":[{"name":"context_type","in":"query","required":false,"schema":{"enum":["global","campaign","account"],"type":"string","description":"Whose library to read. `campaign` and `account` additionally need the matching id below; without it the app reads the GLOBAL library, which is a different set of documents rather than an error.","default":"global","title":"Context Type"},"description":"Whose library to read. `campaign` and `account` additionally need the matching id below; without it the app reads the GLOBAL library, which is a different set of documents rather than an error."},{"name":"campaign_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Campaign id. Only read when `context_type` is `campaign`.","title":"Campaign Id"},"description":"Campaign id. Only read when `context_type` is `campaign`."},{"name":"account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Account id. Only read when `context_type` is `account`.","title":"Account Id"},"description":"Account id. Only read when `context_type` is `account`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DocumentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/detail":{"get":{"tags":["Contacts"],"summary":"Get Contact Detail","description":"The composed contact record the app's detail page renders.\n\n404 when the contact does not exist OR is outside the key's scope - the\ntwo are deliberately indistinguishable.","operationId":"get_contact_detail_contacts__contact_id__detail_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/sequences":{"get":{"tags":["Contacts"],"summary":"Get Contact Sequences","description":"Every sequence this contact is or was enrolled in, with its step and state.","operationId":"get_contact_sequences_contacts__contact_id__sequences_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/lists":{"get":{"tags":["Contacts"],"summary":"Get Contact Lists","description":"The lists this contact belongs to that the key can see.","operationId":"get_contact_lists_contacts__contact_id__lists_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact primary key (`mashup_contacts.id`).","title":"Contact Id"},"description":"Contact primary key (`mashup_contacts.id`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/related":{"post":{"tags":["Contacts"],"summary":"Batch Contact Related","description":"Sequences and/or lists for up to 100 contacts in ONE request. Writes nothing.\n\nUse this instead of looping `GET /contacts/{contact_id}/sequences` or\n`/lists` per contact: the loop spends one rate-limit slot per contact and\nhits 429 on a large book; this spends one per 100.\n\nEach contact gets exactly what its per-contact route returns, through the\nsame access check. A contact that does not exist or is outside the key's\nscope for any requested include comes back `found: false` with no related\nrecords, rather than failing the batch. POST only because the ids are a\nbody; it is tiered as a read.","operationId":"batch_contact_related_contacts_related_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContactRelatedBatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContactRelatedBatchResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/meetings":{"get":{"tags":["Contacts"],"summary":"Get Contact Meetings","description":"Meetings booked with this contact, past and upcoming.","operationId":"get_contact_meetings_contacts__contact_id__meetings_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/signals":{"get":{"tags":["Contacts"],"summary":"Get Contact Signals","description":"Buying signals recorded against this contact.","operationId":"get_contact_signals_contacts__contact_id__signals_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/analysis":{"get":{"tags":["Contacts"],"summary":"Get Contact Analysis","description":"Engagement trend over 7/30/60 days and the strategy it suggests.\n\nRule-based over recorded events, cached briefly. No model call, no spend.","operationId":"get_contact_analysis_contacts__contact_id__analysis_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/tags":{"get":{"tags":["Contacts"],"summary":"Get Contact Tag Ids","description":"The ids of the tags on this contact. Resolve names with `GET /contacts/tags`.","operationId":"get_contact_tag_ids_contacts__contact_id__tags_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/merge/preview":{"get":{"tags":["Contacts"],"summary":"Preview Contact Merge","description":"Side-by-side comparison and blocker check. Writes nothing.","operationId":"preview_contact_merge_contacts__contact_id__merge_preview_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"The contact that SURVIVES the merge.","title":"Contact Id"},"description":"The contact that SURVIVES the merge."},{"name":"secondary","in":"query","required":true,"schema":{"type":"integer","description":"The contact that would be merged AWAY.","title":"Secondary"},"description":"The contact that would be merged AWAY."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/merge":{"post":{"tags":["Contacts"],"summary":"Merge Contact","description":"Merge `secondary_id` INTO this contact. THE SECONDARY STOPS EXISTING.\n\nBoth contacts must be writable by the key; the handler checks both.\nUndo is one merge at a time via `POST /duplicates/undo-merge/{id}`.","operationId":"merge_contact_contacts__contact_id__merge_post","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"The contact that SURVIVES the merge.","title":"Contact Id"},"description":"The contact that SURVIVES the merge."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MergeRecordRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"contacts:delete","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/documents":{"get":{"tags":["Contacts"],"summary":"List Contact Documents","description":"The documents graph8 has generated about this contact.","operationId":"list_contact_documents_contacts__contact_id__documents_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"folder","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only documents in this folder.","title":"Folder"},"description":"Only documents in this folder."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/documents/types/{doc_type}":{"get":{"tags":["Contacts"],"summary":"Get Contact Document","description":"The current document of one type for this contact.","operationId":"get_contact_document_contacts__contact_id__documents_types__doc_type__get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"doc_type","in":"path","required":true,"schema":{"type":"string","description":"Document type, e.g. `contact_brief`.","title":"Doc Type"},"description":"Document type, e.g. `contact_brief`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/documents/types/{doc_type}/generate":{"post":{"tags":["Contacts"],"summary":"Generate Contact Document","description":"Generate one document of this type. SPENDS CREDITS. Unknown types are a 400.","operationId":"generate_contact_document_contacts__contact_id__documents_types__doc_type__generate_post","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"doc_type","in":"path","required":true,"schema":{"type":"string","description":"Document type.","title":"Doc Type"},"description":"Document type."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/documents/types/{doc_type}/regenerate":{"post":{"tags":["Contacts"],"summary":"Regenerate Contact Document","description":"Throw away this document and generate it again. SPENDS CREDITS.","operationId":"regenerate_contact_document_contacts__contact_id__documents_types__doc_type__regenerate_post","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"doc_type","in":"path","required":true,"schema":{"type":"string","description":"Document type.","title":"Doc Type"},"description":"Document type."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/documents/{document_id}":{"put":{"tags":["Contacts"],"summary":"Update Contact Document","description":"Edit a generated document's content or structured data by hand.","operationId":"update_contact_document_contacts__contact_id__documents__document_id__put","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Document Id"},"description":"Document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContactDocumentUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Contacts"],"summary":"Delete Contact Document","description":"Delete one generated document PERMANENTLY.","operationId":"delete_contact_document_contacts__contact_id__documents__document_id__delete","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Document Id"},"description":"Document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"contacts:delete","x-graph8-lifecycle":"active"}},"/duplicates/settings":{"get":{"tags":["Contacts"],"summary":"Get Duplicate Settings","description":"The org's merge rules: field winners, auto-merge, detection-rule overrides.\n\nAdmin-only in the app (manage scope on every governed object); the same\ncheck runs here, inside the handler.","operationId":"get_duplicate_settings_duplicates_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"},"put":{"tags":["Contacts"],"summary":"Update Duplicate Settings","description":"REPLACE the org's merge settings wholesale. Partial updates are not supported.\n\nRead with `GET /duplicates/settings`, change what you need, and send the\nwhole tree back - a missing section falls back to the platform default.","operationId":"update_duplicate_settings_duplicates_settings_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"The FULL settings tree, as `GET` returns it.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/duplicates/detection/run":{"post":{"tags":["Contacts"],"summary":"Run Duplicate Detection","description":"Scan the org for duplicates of one record type now. Admin-only.\n\nRate-limited by the app to once per 15 minutes per record type (429 with\nthe wait). Finds suggestions only - nothing is merged.","operationId":"run_duplicate_detection_duplicates_detection_run_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RunDetectionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/duplicates/detection/runs":{"get":{"tags":["Contacts"],"summary":"List Duplicate Detection Runs","description":"Recent duplicate-detection runs - when the last check ran and what it found.","operationId":"list_duplicate_detection_runs_duplicates_detection_runs_get","parameters":[{"name":"entity_type","in":"query","required":false,"schema":{"anyOf":[{"enum":["contact","company","deal"],"type":"string"},{"type":"null"}],"description":"Only runs for this record type.","title":"Entity Type"},"description":"Only runs for this record type."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"description":"How many runs, newest first.","default":10,"title":"Limit"},"description":"How many runs, newest first."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/workflow-executions":{"get":{"tags":["Contacts"],"summary":"List Record Workflow Executions","description":"Workflow runs for one row of a list, newest first.","operationId":"list_record_workflow_executions_contacts_workflow_executions_get","parameters":[{"name":"list_id","in":"query","required":true,"schema":{"type":"integer","description":"The list the row belongs to.","title":"List Id"},"description":"The list the row belongs to."},{"name":"record_id","in":"query","required":true,"schema":{"type":"integer","description":"The row (contact) id.","title":"Record Id"},"description":"The row (contact) id."},{"name":"workflow_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only runs of this workflow.","title":"Workflow Id"},"description":"Only runs of this workflow."},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only this status.","title":"Status"},"description":"Only this status."},{"name":"include_events","in":"query","required":false,"schema":{"type":"boolean","description":"Include each run's step events.","default":false,"title":"Include Events"},"description":"Include each run's step events."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/workflow-executions/run":{"post":{"tags":["Contacts"],"summary":"Run Record Workflow","description":"Run a list workflow over rows. SPENDS CREDITS when its steps enrich or call a model.\n\n`run_mode=all` runs over every row in the list, so the spend is bounded\nby the list, not the request.","operationId":"run_record_workflow_contacts_workflow_executions_run_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RunRecordWorkflowRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/contacts/workflow-executions/{execution_id}/pause":{"post":{"tags":["Contacts"],"summary":"Pause Record Workflow Execution","description":"Pause a running row workflow at its next step boundary.","operationId":"pause_record_workflow_execution_contacts_workflow_executions__execution_id__pause_post","parameters":[{"name":"execution_id","in":"path","required":true,"schema":{"type":"string","description":"Workflow execution id.","title":"Execution Id"},"description":"Workflow execution id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/workflow-executions/{execution_id}/resume":{"post":{"tags":["Contacts"],"summary":"Resume Record Workflow Execution","description":"Resume a paused row workflow.","operationId":"resume_record_workflow_execution_contacts_workflow_executions__execution_id__resume_post","parameters":[{"name":"execution_id","in":"path","required":true,"schema":{"type":"string","description":"Workflow execution id.","title":"Execution Id"},"description":"Workflow execution id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/workflow-executions/{execution_id}/cancel":{"post":{"tags":["Contacts"],"summary":"Cancel Record Workflow Execution","description":"Cancel a row workflow. Steps already run are not undone.","operationId":"cancel_record_workflow_execution_contacts_workflow_executions__execution_id__cancel_post","parameters":[{"name":"execution_id","in":"path","required":true,"schema":{"type":"string","description":"Workflow execution id.","title":"Execution Id"},"description":"Workflow execution id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"contacts:delete","x-graph8-lifecycle":"active"}},"/contacts/workflow-executions/{execution_id}/approve":{"post":{"tags":["Contacts"],"summary":"Decide Record Workflow Execution","description":"Approve or reject a row workflow paused at an approval step.","operationId":"decide_record_workflow_execution_contacts_workflow_executions__execution_id__approve_post","parameters":[{"name":"execution_id","in":"path","required":true,"schema":{"type":"string","description":"Workflow execution id.","title":"Execution Id"},"description":"Workflow execution id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApproveExecutionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/bulk-get":{"post":{"tags":["Contacts"],"summary":"Bulk Get Contacts","description":"Full records for up to 100 contacts in ONE request. Writes nothing.\n\nUse this instead of looping `GET /contacts/{contact_id}`: `GET /contacts`\nreturns a lean summary per contact, and the loop spends one rate-limit slot per\ncontact to get the other fields. Each item is exactly what the per-contact\nroute returns, through the same access check. A contact that does not exist\nor is outside the key's scope comes back `found: false`, rather than failing\nthe batch. POST only because the ids are a body; it is tiered as a read.","operationId":"bulk_get_contacts_contacts_bulk_get_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContactBulkGetRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContactBulkGetResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/detail":{"get":{"tags":["Companies"],"summary":"Get Company Detail","description":"The composed company record the app's detail page renders.\n\nFirmographics, owner, CRM overlay and custom column values in one read.","operationId":"get_company_detail_companies__company_id__detail_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"id_kind","in":"query","required":false,"schema":{"enum":["auto","company_id"],"type":"string","description":"`auto` resolves the graph8 company id (integer or UUID); `company_id` resolves the global company business key.","default":"auto","title":"Id Kind"},"description":"`auto` resolves the graph8 company id (integer or UUID); `company_id` resolves the global company business key."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/signals":{"get":{"tags":["Companies"],"summary":"Get Company Signals","description":"Buying signals recorded against this company, newest first.","operationId":"get_company_signals_companies__company_id__signals_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/contacts/{contact_id}":{"post":{"tags":["Companies"],"summary":"Attach Company Contact","description":"Link a contact to this company. The contact is gated inside the app handler.","operationId":"attach_company_contact_companies__company_id__contacts__contact_id__post","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"contact_id","in":"path","required":true,"schema":{"type":"string","description":"Contact to link to the company.","title":"Contact Id"},"description":"Contact to link to the company."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Companies"],"summary":"Remove Company Contact","description":"Unlink a contact from this company. Neither record is deleted.","operationId":"remove_company_contact_companies__company_id__contacts__contact_id__delete","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"contact_id","in":"path","required":true,"schema":{"type":"string","description":"Contact to unlink from the company.","title":"Contact Id"},"description":"Contact to unlink from the company."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"companies:delete","x-graph8-lifecycle":"active"}},"/companies/{company_id}/tasks":{"get":{"tags":["Companies"],"summary":"List Company Tasks","description":"Tasks attached to this company that the key can see.","operationId":"list_company_tasks_companies__company_id__tasks_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"task_status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only tasks in this status.","title":"Task Status"},"description":"Only tasks in this status."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"},"post":{"tags":["Companies"],"summary":"Create Company Task","description":"Create a task attached to this company.","operationId":"create_company_task_companies__company_id__tasks_post","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CompanyTaskCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/companies/{company_id}/merge/preview":{"get":{"tags":["Companies"],"summary":"Preview Company Merge","description":"Side-by-side comparison and blocker check. Writes nothing.\n\nBoth companies are authorised inside the app handler.","operationId":"preview_company_merge_companies__company_id__merge_preview_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"The company that SURVIVES the merge.","title":"Company Id"},"description":"The company that SURVIVES the merge."},{"name":"secondary","in":"query","required":true,"schema":{"type":"integer","description":"The company that would be merged AWAY.","title":"Secondary"},"description":"The company that would be merged AWAY."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/merge":{"post":{"tags":["Companies"],"summary":"Merge Company","description":"Merge `secondary_id` INTO this company. THE SECONDARY STOPS EXISTING.\n\nIts contacts, deals and activity move onto the survivor. Undo is one merge\nat a time through `POST /duplicates/undo-merge/{merge_history_id}`.\nPreview first. 409 when a blocker refuses the merge.","operationId":"merge_company_companies__company_id__merge_post","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"The company that SURVIVES the merge.","title":"Company Id"},"description":"The company that SURVIVES the merge."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MergeRecordRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"companies:delete","x-graph8-lifecycle":"active"}},"/companies/{company_id}/documents":{"get":{"tags":["Companies"],"summary":"List Company Documents","description":"The intelligence documents generated for this company.","operationId":"list_company_documents_companies__company_id__documents_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"folder","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only documents in this folder.","title":"Folder"},"description":"Only documents in this folder."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/documents/{document_id}":{"delete":{"tags":["Companies"],"summary":"Delete Company Document","description":"Delete one generated document PERMANENTLY. Regenerating it spends credits.","operationId":"delete_company_document_companies__company_id__documents__document_id__delete","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Document Id"},"description":"Document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"companies:delete","x-graph8-lifecycle":"active"}},"/companies/{company_id}/documents/types/{doc_type}/generate":{"post":{"tags":["Companies"],"summary":"Generate Company Document","description":"Generate ONE document of this type. SPENDS CREDITS. Asynchronous.\n\n`types/` separates the document TYPE from a document id, so this can\nnever be confused with `DELETE /companies/{id}/documents/{document_id}`.","operationId":"generate_company_document_companies__company_id__documents_types__doc_type__generate_post","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"doc_type","in":"path","required":true,"schema":{"type":"string","description":"Document type, e.g. `account_brief`.","title":"Doc Type"},"description":"Document type, e.g. `account_brief`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/companies/{company_id}/documents/types/{doc_type}/regenerate":{"post":{"tags":["Companies"],"summary":"Regenerate Company Document","description":"Throw away this document and generate it again. SPENDS CREDITS.","operationId":"regenerate_company_document_companies__company_id__documents_types__doc_type__regenerate_post","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"doc_type","in":"path","required":true,"schema":{"type":"string","description":"Document type.","title":"Doc Type"},"description":"Document type."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/companies/{company_id}/intelligence-data/{data_type}":{"get":{"tags":["Companies"],"summary":"Get Company Intelligence Data","description":"The raw intelligence record of one type - the input the documents are written from.","operationId":"get_company_intelligence_data_companies__company_id__intelligence_data__data_type__get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"data_type","in":"path","required":true,"schema":{"type":"string","description":"Intelligence data type, e.g. `tech_stack`.","title":"Data Type"},"description":"Intelligence data type, e.g. `tech_stack`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/workflows/{workflow_type}/start":{"post":{"tags":["Companies"],"summary":"Start Company Workflow","description":"Start one intelligence workflow for this company. SPENDS CREDITS.\n\nPoll `GET /companies/{company_id}/workflow-status`.","operationId":"start_company_workflow_companies__company_id__workflows__workflow_type__start_post","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"workflow_type","in":"path","required":true,"schema":{"$ref":"#/components/schemas/CompanyWorkflowType","description":"Which workflow to run."},"description":"Which workflow to run."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/companies/{company_id}/billing-prefill/refresh":{"post":{"tags":["Companies"],"summary":"Refresh Company Billing Prefill","description":"Recompute the billing details suggested for this company's quotes.","operationId":"refresh_company_billing_prefill_companies__company_id__billing_prefill_refresh_post","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/companies/enrich/bulk":{"post":{"tags":["Companies"],"summary":"Bulk Enrich Companies","description":"Enrich EVERY company in the org that still lacks firmographics. SPENDS CREDITS.\n\nOne paid provider lookup per company. There is no selection: the scope is\nthe whole org, so the spend is bounded by the org's data, not the request.","operationId":"bulk_enrich_companies_companies_enrich_bulk_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/companies/enrich/people/bulk":{"post":{"tags":["Companies"],"summary":"Bulk Enrich Company People","description":"Enrich the people of every company in the org. SPENDS CREDITS. Org-wide.","operationId":"bulk_enrich_company_people_companies_enrich_people_bulk_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/companies/enrich/stakeholders/bulk":{"post":{"tags":["Companies"],"summary":"Bulk Enrich Company Stakeholders","description":"Find and enrich the buying committee at every company. SPENDS CREDITS. Org-wide.","operationId":"bulk_enrich_company_stakeholders_companies_enrich_stakeholders_bulk_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/meeting-transcripts":{"get":{"tags":["Meetings"],"summary":"List Meeting Transcripts","description":"Transcripts the key can see, newest first, with a total for paging.","operationId":"list_meeting_transcripts_meeting_transcripts_get","parameters":[{"name":"transcript_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"`account`, `client` or `internal`.","title":"Transcript Type"},"description":"`account`, `client` or `internal`."},{"name":"account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only transcripts filed under this account.","title":"Account Id"},"description":"Only transcripts filed under this account."},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"description":"Earliest meeting date.","title":"Date From"},"description":"Earliest meeting date."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"description":"Latest meeting date.","title":"Date To"},"description":"Latest meeting date."},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Match in the title or the transcript text.","title":"Search"},"description":"Match in the title or the transcript text."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Page size.","default":50,"title":"Limit"},"description":"Page size."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Rows to skip.","default":0,"title":"Offset"},"description":"Rows to skip."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/meeting-transcripts/stats":{"get":{"tags":["Meetings"],"summary":"Get Meeting Transcript Stats","description":"Org-wide counts: transcripts by type, how many are filed, recent volume.","operationId":"get_meeting_transcript_stats_meeting_transcripts_stats_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/meeting-transcripts/coaching-queue":{"get":{"tags":["Meetings"],"summary":"Get Meeting Coaching Queue","description":"Reviewed meetings flagged for a manager's attention. MANAGER ONLY.\n\nRequires `meetings:see_all` or a privileged org role on the key's minter;\notherwise 403, because it surfaces every rep's scores.","operationId":"get_meeting_coaching_queue_meeting_transcripts_coaching_queue_get","parameters":[{"name":"target","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only reviews for this pipeline target.","title":"Target"},"description":"Only reviews for this pipeline target."},{"name":"only_unreviewed","in":"query","required":false,"schema":{"type":"boolean","description":"Only reviews no manager has acknowledged.","default":false,"title":"Only Unreviewed"},"description":"Only reviews no manager has acknowledged."},{"name":"min_score","in":"query","required":false,"schema":{"type":"integer","maximum":40,"minimum":0,"description":"Lowest review score to include.","default":0,"title":"Min Score"},"description":"Lowest review score to include."},{"name":"max_score","in":"query","required":false,"schema":{"type":"integer","maximum":40,"minimum":0,"description":"Highest review score to include.","default":40,"title":"Max Score"},"description":"Highest review score to include."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"How many reviews.","default":50,"title":"Limit"},"description":"How many reviews."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/meeting-transcripts/{transcript_id}":{"get":{"tags":["Meetings"],"summary":"Get Meeting Transcript","description":"The full transcript. 403 unless the key's minter took part or can see all meetings.","operationId":"get_meeting_transcript_meeting_transcripts__transcript_id__get","parameters":[{"name":"transcript_id","in":"path","required":true,"schema":{"type":"string","description":"Transcript id.","title":"Transcript Id"},"description":"Transcript id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Meetings"],"summary":"Delete Meeting Transcript","description":"Delete a transcript PERMANENTLY. ORG ADMIN ONLY (checked by the app handler).","operationId":"delete_meeting_transcript_meeting_transcripts__transcript_id__delete","parameters":[{"name":"transcript_id","in":"path","required":true,"schema":{"type":"string","description":"Transcript id.","title":"Transcript Id"},"description":"Transcript id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/meeting-transcripts/{transcript_id}/follow-up-draft":{"post":{"tags":["Meetings"],"summary":"Draft Meeting Follow Up","description":"A follow-up email draft grounded in this meeting. NOTHING IS SENT.\n\nReturns the draft written at import time when there is one; generates on\ndemand (a model call, which spends credits) when there is none or when\n`regenerate=true`.","operationId":"draft_meeting_follow_up_meeting_transcripts__transcript_id__follow_up_draft_post","parameters":[{"name":"transcript_id","in":"path","required":true,"schema":{"type":"string","description":"Transcript id.","title":"Transcript Id"},"description":"Transcript id."},{"name":"regenerate","in":"query","required":false,"schema":{"type":"boolean","description":"Write a fresh draft even when one is stored. SPENDS CREDITS.","default":false,"title":"Regenerate"},"description":"Write a fresh draft even when one is stored. SPENDS CREDITS."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"}},"/meeting-transcripts/{transcript_id}/account":{"patch":{"tags":["Meetings"],"summary":"Link Meeting Transcript Account","description":"File this transcript under an account, overriding the automatic categoriser.","operationId":"link_meeting_transcript_account_meeting_transcripts__transcript_id__account_patch","parameters":[{"name":"transcript_id","in":"path","required":true,"schema":{"type":"string","description":"Transcript id.","title":"Transcript Id"},"description":"Transcript id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LinkTranscriptAccountRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/meeting-transcripts/{transcript_id}/review":{"get":{"tags":["Meetings"],"summary":"Get Meeting Review","description":"The AI review of this meeting: score, stage elements hit and missed, coaching notes.\n\n404 until the review has run. A review that ran but was skipped (orphan\nmeeting, transcript too short) returns `skipped: true` with the reason.","operationId":"get_meeting_review_meeting_transcripts__transcript_id__review_get","parameters":[{"name":"transcript_id","in":"path","required":true,"schema":{"type":"string","description":"Transcript id.","title":"Transcript Id"},"description":"Transcript id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/meeting-transcripts/{transcript_id}/review/regenerate":{"post":{"tags":["Meetings"],"summary":"Regenerate Meeting Review","description":"Run the meeting review again. SPENDS CREDITS on every call.\n\nFor a review that failed, or after the transcript was re-linked to the\nright deal.","operationId":"regenerate_meeting_review_meeting_transcripts__transcript_id__review_regenerate_post","parameters":[{"name":"transcript_id","in":"path","required":true,"schema":{"type":"string","description":"Transcript id.","title":"Transcript Id"},"description":"Transcript id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"}},"/meeting-transcripts/{transcript_id}/review/acknowledge":{"post":{"tags":["Meetings"],"summary":"Acknowledge Meeting Review","description":"Mark a review acknowledged in the coaching queue. MANAGER ONLY.","operationId":"acknowledge_meeting_review_meeting_transcripts__transcript_id__review_acknowledge_post","parameters":[{"name":"transcript_id","in":"path","required":true,"schema":{"type":"string","description":"Transcript id.","title":"Transcript Id"},"description":"Transcript id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/stage-readiness":{"get":{"tags":["Meetings"],"summary":"Get Deal Stage Readiness","description":"How ready this deal is for its next stage, from the evidence in its meeting reviews.","operationId":"get_deal_stage_readiness_deals__deal_id__stage_readiness_get","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/memory":{"get":{"tags":["Meetings"],"summary":"Get Deal Memory","description":"Everything the meetings on this deal established: people, pains, commitments, risks.","operationId":"get_deal_memory_deals__deal_id__memory_get","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/next-best-step":{"post":{"tags":["Meetings"],"summary":"Suggest Deal Next Best Step","description":"One recommended next action for this deal. SPENDS CREDITS. Writes nothing.\n\nPOST because every call is a fresh model call. Gated on READ access to\nthe deal, as in the app: recommending is not editing. 502 when the model\ncall fails.","operationId":"suggest_deal_next_best_step_deals__deal_id__next_best_step_post","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/advance-stage":{"post":{"tags":["Meetings"],"summary":"Advance Deal Stage","description":"Move the deal to its next stage when the meeting evidence says it is ready.\n\nA real stage change: audited, and it emits the same stage-change event a\nperson moving the deal would. Refused when the readiness check fails.","operationId":"advance_deal_stage_deals__deal_id__advance_stage_post","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/deals/analytics":{"get":{"tags":["Deals"],"summary":"Get Deal Analytics","description":"Pipeline totals, stage breakdown, win rate and velocity over the deals the key can see.","operationId":"get_deal_analytics_deals_analytics_get","parameters":[{"name":"pipeline_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only this pipeline.","title":"Pipeline Id"},"description":"Only this pipeline."},{"name":"owner_ids","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"string"}},{"type":"null"}],"description":"Only these owners. Repeatable.","title":"Owner Ids"},"description":"Only these owners. Repeatable."},{"name":"stage_ids","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"string"}},{"type":"null"}],"description":"Only these stages. Repeatable.","title":"Stage Ids"},"description":"Only these stages. Repeatable."},{"name":"close_date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Close date lower bound, YYYY-MM-DD.","title":"Close Date From"},"description":"Close date lower bound, YYYY-MM-DD."},{"name":"close_date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Close date upper bound, YYYY-MM-DD.","title":"Close Date To"},"description":"Close date upper bound, YYYY-MM-DD."},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Match on deal or account name.","title":"Search"},"description":"Match on deal or account name."},{"name":"segmentFilter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Advanced filter tree as JSON, the same one `GET /deals` accepts. 400 if unparseable.","title":"Segmentfilter"},"description":"Advanced filter tree as JSON, the same one `GET /deals` accepts. 400 if unparseable."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/line-items":{"get":{"tags":["Deals"],"summary":"List Deal Line Items","description":"A deal's line items, its derived amount, and whether it disagrees with its linked quote.","operationId":"list_deal_line_items_deals__deal_id__line_items_get","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id.","title":"Deal Id"},"description":"Deal id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealLineItemsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"put":{"tags":["Deals"],"summary":"Replace Deal Line Items","description":"Replace a deal's line items. The FULL set, not a delta.\n\nA non-empty set makes the deal amount the sum of the lines (audited in the\ndeal history). An empty set clears the lines and keeps the typed amount.","operationId":"replace_deal_line_items_deals__deal_id__line_items_put","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id.","title":"Deal Id"},"description":"Deal id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DealLineItemsReplaceBody"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealLineItemsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/deals/stage-velocity":{"get":{"tags":["Deals"],"summary":"Get Deal Stage Velocity","description":"Time in stage, stage conversion and stuck deals over the deals the key can see.","operationId":"get_deal_stage_velocity_deals_stage_velocity_get","parameters":[{"name":"pipeline_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only this pipeline (UUID).","title":"Pipeline Id"},"description":"Only this pipeline (UUID)."},{"name":"owner_ids","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"string"}},{"type":"null"}],"description":"Only these owners. Repeatable, at most 100.","title":"Owner Ids"},"description":"Only these owners. Repeatable, at most 100."},{"name":"stuck_threshold_days","in":"query","required":false,"schema":{"type":"integer","maximum":3650,"minimum":1,"description":"A deal with no stage change in this many days is 'stuck'.","default":30,"title":"Stuck Threshold Days"},"description":"A deal with no stage change in this many days is 'stuck'."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealStageVelocityPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/touches":{"get":{"tags":["Deals"],"summary":"Get Deal Touches","description":"The deal's touch timeline: every matched email, meeting, sequence step and manual touch, newest first.\n\nCached; `timeline_built_at` says when. 404 for a deal the key cannot see.","operationId":"get_deal_touches_deals__deal_id__touches_get","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealTouchTimelinePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"post":{"tags":["Deals"],"summary":"Add Deal Touch","description":"Record a touch by hand (a call, a visit). Needs write access to the deal; the person must be on the deal.","operationId":"add_deal_touch_deals__deal_id__touches_post","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ManualTouchRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealTouchTimelinePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/touches/search":{"post":{"tags":["Deals"],"summary":"Search Deal Touches","description":"Propose touches from the deal owner's Sent mail. WRITES NOTHING; `accept` records the ones you pick.\n\nPersonal key only: the search reads the OWNER's mailbox, so the caller must be the deal owner or an org admin\n(an admin's search of someone else's mailbox is audit-logged). 409 `deal_touch_disabled` /\n`deal_touch_sent_capture_disabled` while the organisation has not turned capture on.","operationId":"search_deal_touches_deals__deal_id__touches_search_post","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealTouchSearchPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/touches/search/accept":{"post":{"tags":["Deals"],"summary":"Accept Deal Touches","description":"Record the candidates `touches/search` returned. Each needs its signed `token` (30 minutes); the person must be on the deal.","operationId":"accept_deal_touches_deals__deal_id__touches_search_accept_post","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AcceptTouchesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealTouchTimelinePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/settings/deal-touch":{"get":{"tags":["Deals"],"summary":"Get Deal Touch Settings","description":"Whether deal touches and sent-mail capture are on for the organisation, the look-back window and who set them. Admin only.","operationId":"get_deal_touch_settings_settings_deal_touch_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealTouchSettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"put":{"tags":["Deals"],"summary":"Update Deal Touch Settings","description":"Turn deal touches or sent-mail capture on or off, or change the look-back window. Admin only; send at least one field.\n\nChanging the window rebuilds every cached timeline in the background (`rebuild_pending`). Sent-mail capture cannot\nbe on while `enabled` is false.","operationId":"update_deal_touch_settings_settings_deal_touch_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DealTouchSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealTouchSettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/settings/deal-touch/me":{"get":{"tags":["Deals"],"summary":"Get My Deal Touch Status","description":"The caller's own deal-touch status: has the sent-mail disclosure been seen, and is a Google mailbox connected. Personal key only.","operationId":"get_my_deal_touch_status_settings_deal_touch_me_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealTouchSettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/settings/deal-touch/disclosure-ack":{"post":{"tags":["Deals"],"summary":"Acknowledge Deal Touch Disclosure","description":"Record that the caller has read the sent-mail capture disclosure. Personal key only; idempotent.","operationId":"acknowledge_deal_touch_disclosure_settings_deal_touch_disclosure_ack_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/reports/pipeline-by-source":{"get":{"tags":["Deals"],"summary":"Get Pipeline By Source","description":"New pipeline by source channel for a period against the one before it, over the deals the key can see.","operationId":"get_pipeline_by_source_reports_pipeline_by_source_get","parameters":[{"name":"model","in":"query","required":false,"schema":{"enum":["first","last","any"],"type":"string","description":"Credit the first, last or any touch channel.","default":"first","title":"Model"},"description":"Credit the first, last or any touch channel."},{"name":"from","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"description":"First day (default: 30 days ago).","title":"From"},"description":"First day (default: 30 days ago)."},{"name":"to","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"description":"Last day (default: today).","title":"To"},"description":"Last day (default: today)."},{"name":"owner_id","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"string"}},{"type":"null"}],"description":"Only deals owned by these people. Repeatable; a merged rep option is one value.","title":"Owner Id"},"description":"Only deals owned by these people. Repeatable; a merged rep option is one value."},{"name":"pipeline_id","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"string","format":"uuid"}},{"type":"null"}],"description":"Only these pipelines. Repeatable.","title":"Pipeline Id"},"description":"Only these pipelines. Repeatable."},{"name":"sequence_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Sequence Id"}},{"name":"tz","in":"query","required":false,"schema":{"type":"string","maxLength":64,"description":"IANA time zone; days and months are local to it.","default":"UTC","title":"Tz"},"description":"IANA time zone; days and months are local to it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PipelineBySourcePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/reports/pipeline-by-source/deals":{"get":{"tags":["Deals"],"summary":"List Pipeline By Source Deals","description":"The deals behind one cell of the pipeline-by-source report, largest first, over the deals the key can see.","operationId":"list_pipeline_by_source_deals_reports_pipeline_by_source_deals_get","parameters":[{"name":"model","in":"query","required":false,"schema":{"enum":["first","last","any"],"type":"string","default":"first","title":"Model"}},{"name":"from","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"From"}},{"name":"to","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"To"}},{"name":"owner_id","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"string"}},{"type":"null"}],"description":"Only deals owned by these people. Repeatable; a merged rep option is one value.","title":"Owner Id"},"description":"Only deals owned by these people. Repeatable; a merged rep option is one value."},{"name":"pipeline_id","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"string","format":"uuid"}},{"type":"null"}],"description":"Only these pipelines. Repeatable.","title":"Pipeline Id"},"description":"Only these pipelines. Repeatable."},{"name":"sequence_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Sequence Id"}},{"name":"period","in":"query","required":false,"schema":{"enum":["current","previous"],"type":"string","default":"current","title":"Period"}},{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"enum":["outbound","inbound","meeting","unknown"],"type":"string"},{"type":"null"}],"description":"Only deals credited to this source.","title":"Source"},"description":"Only deals credited to this source."},{"name":"channel","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":32},{"type":"null"}],"title":"Channel"}},{"name":"month","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^\\d{4}-\\d{2}$"},{"type":"null"}],"description":"`YYYY-MM`.","title":"Month"},"description":"`YYYY-MM`."},{"name":"rep","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":32},{"type":"null"}],"description":"A rep key from the report's `reps`.","title":"Rep"},"description":"A rep key from the report's `reps`."},{"name":"assisted","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Assisted"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":25,"title":"Limit"}},{"name":"tz","in":"query","required":false,"schema":{"type":"string","maxLength":64,"default":"UTC","title":"Tz"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PipelineBySourceDealsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/reports/pipeline-by-channel":{"get":{"tags":["Deals"],"summary":"Get Pipeline By Channel","description":"Pipeline by touch channel (email, call, meeting, sequence ...) and by rep, over the deals the key can see.","operationId":"get_pipeline_by_channel_reports_pipeline_by_channel_get","parameters":[{"name":"model","in":"query","required":false,"schema":{"enum":["first","last","any"],"type":"string","default":"first","title":"Model"}},{"name":"from","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"From"}},{"name":"to","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"To"}},{"name":"owner_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id"}},{"name":"sequence_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Sequence Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PipelineByChannelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/stagegate/rules":{"get":{"tags":["Stagegate"],"summary":"List Stagegate Rules","description":"The organisation's Stagegate rules. `can_edit` says whether this key may change them; `reconciled` is false while the workspace is still being set up.","operationId":"list_stagegate_rules_stagegate_rules_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateRulesPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"post":{"tags":["Stagegate"],"summary":"Create Stagegate Rule","description":"Create a rule. Admin only; `name` and `conditions` are required. An enabled rule is checked against open deals straight away (in the background).","operationId":"create_stagegate_rule_stagegate_rules_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StagegateRuleRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateRulesPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/stagegate/rules/{rule_id}":{"patch":{"tags":["Stagegate"],"summary":"Update Stagegate Rule","description":"Change a rule; send only what changes. Admin only. Switching it off clears its open violations; editing its logic or switching it on rechecks open deals.","operationId":"update_stagegate_rule_stagegate_rules__rule_id__patch","parameters":[{"name":"rule_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Rule id (UUID).","title":"Rule Id"},"description":"Rule id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StagegateRuleRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateRulesPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Stagegate"],"summary":"Delete Stagegate Rule","description":"Delete a rule and clear its open violations. Admin only.","operationId":"delete_stagegate_rule_stagegate_rules__rule_id__delete","parameters":[{"name":"rule_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Rule id (UUID).","title":"Rule Id"},"description":"Rule id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"deals:delete","x-graph8-lifecycle":"active"}},"/stagegate/rule-packs":{"get":{"tags":["Stagegate"],"summary":"List Stagegate Rule Packs","description":"Ready-made rule packs, plus \"starter rules from your checklists\" when the organisation has stage checklists.","operationId":"list_stagegate_rule_packs_stagegate_rule_packs_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegatePacksPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/stagegate/rule-packs/{pack_id}/preview":{"post":{"tags":["Stagegate"],"summary":"Preview Stagegate Rule Pack","description":"The pack bound to a pipeline: its stages, the stage picked per slot and each rule (flagging rules already present). Changes nothing. Admin only.","operationId":"preview_stagegate_rule_pack_stagegate_rule_packs__pack_id__preview_post","parameters":[{"name":"pack_id","in":"path","required":true,"schema":{"type":"string","description":"Template pack id.","title":"Pack Id"},"description":"Template pack id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StagegatePackPreviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegatePacksPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/stagegate/rule-packs/{pack_id}/install":{"post":{"tags":["Stagegate"],"summary":"Install Stagegate Rule Pack","description":"Add the chosen rules of a pack. Admin only. Returns `added`, `skipped_identical` and `installed_off`; enabled rules are checked against open deals in the background.","operationId":"install_stagegate_rule_pack_stagegate_rule_packs__pack_id__install_post","parameters":[{"name":"pack_id","in":"path","required":true,"schema":{"type":"string","description":"Template pack id.","title":"Pack Id"},"description":"Template pack id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StagegatePackInstallRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegatePacksPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/stagegate/settings":{"get":{"tags":["Stagegate"],"summary":"Get Stagegate Settings","description":"How long a violation waits before it escalates and the grace period, plus the organisation time zone.","operationId":"get_stagegate_settings_stagegate_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateSettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"put":{"tags":["Stagegate"],"summary":"Update Stagegate Settings","description":"Set `escalate_after_days` (1 to 30) and `grace_days` (0 to 14). Admin only; both are required.","operationId":"update_stagegate_settings_stagegate_settings_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StagegateSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateSettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/stagegate/status":{"get":{"tags":["Stagegate"],"summary":"Get Stagegate Status","description":"Cheap probe: is the workspace reconciled, is any rule enabled, may this key edit. 404 while the organisation is off the Stagegate allowlist.","operationId":"get_stagegate_status_stagegate_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateViewPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/stagegate/board":{"get":{"tags":["Stagegate"],"summary":"Get Stagegate Board","description":"Open violations by rule and by deal over the deals the key can see.","operationId":"get_stagegate_board_stagegate_board_get","parameters":[{"name":"scope","in":"query","required":false,"schema":{"anyOf":[{"enum":["own","team","all"],"type":"string"},{"type":"null"}],"description":"`own`, `team` or `all`; defaults to the widest this key may see (`allowed_scopes`).","title":"Scope"},"description":"`own`, `team` or `all`; defaults to the widest this key may see (`allowed_scopes`)."},{"name":"filter","in":"query","required":false,"schema":{"enum":["all","zero","escalation"],"type":"string","default":"all","title":"Filter"}},{"name":"rule_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"description":"Only violations of this rule.","title":"Rule Id"},"description":"Only violations of this rule."},{"name":"owner_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only this owner's deals.","title":"Owner Id"},"description":"Only this owner's deals."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateViewPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/stagegate/queue":{"get":{"tags":["Stagegate"],"summary":"Get Stagegate Queue","description":"The caller's OWN deals with open violations, most urgent first. Personal key only.","operationId":"get_stagegate_queue_stagegate_queue_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateViewPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/stagegate/attention":{"get":{"tags":["Stagegate"],"summary":"Get Stagegate Attention","description":"What needs the caller's attention across their own deals (the Desk summary). Personal key only.","operationId":"get_stagegate_attention_stagegate_attention_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateViewPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/stagegate/trend":{"get":{"tags":["Stagegate"],"summary":"Get Stagegate Trend","description":"Daily open-violation counts for the last 30 days over the deals the key can see.","operationId":"get_stagegate_trend_stagegate_trend_get","parameters":[{"name":"scope","in":"query","required":false,"schema":{"anyOf":[{"enum":["own","team","all"],"type":"string"},{"type":"null"}],"title":"Scope"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateViewPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/stagegate/rankings":{"get":{"tags":["Stagegate"],"summary":"Get Stagegate Rankings","description":"Reps ranked by clean days and streaks over the deals the key can see.","operationId":"get_stagegate_rankings_stagegate_rankings_get","parameters":[{"name":"scope","in":"query","required":false,"schema":{"anyOf":[{"enum":["own","team","all"],"type":"string"},{"type":"null"}],"title":"Scope"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateViewPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/stagegate/deals/{deal_id}/violations":{"get":{"tags":["Stagegate"],"summary":"Get Stagegate Deal Violations","description":"One deal's open violations, what evidence is missing and how to fix each. 404 for a deal the key cannot see.","operationId":"get_stagegate_deal_violations_stagegate_deals__deal_id__violations_get","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateDealPanelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/stagegate/deals/{deal_id}/recheck":{"post":{"tags":["Stagegate"],"summary":"Recheck Stagegate Deal","description":"Recheck one deal now (after logging a note or editing it) and return its refreshed panel. 404 for a deal the key cannot see.","operationId":"recheck_stagegate_deal_stagegate_deals__deal_id__recheck_post","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/StagegateQuickFixRequest"},{"type":"null"}],"title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateDealPanelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/stagegate/deals/{deal_id}/attestations":{"post":{"tags":["Stagegate"],"summary":"Attest Stagegate Evidence","description":"Mark an evidence item covered, with the note saying how. Personal key only: it is recorded as that person's statement, never as AI evidence. Needs write access to the deal.","operationId":"attest_stagegate_evidence_stagegate_deals__deal_id__attestations_post","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StagegateAttestationRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateDealPanelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/stagegate/violations/{violation_id}/snooze":{"post":{"tags":["Stagegate"],"summary":"Snooze Stagegate Violation","description":"Snooze one violation until a date, with a reason. Only the deal's OWNER may (403 otherwise); personal key only.","operationId":"snooze_stagegate_violation_stagegate_violations__violation_id__snooze_post","parameters":[{"name":"violation_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Violation id (UUID).","title":"Violation Id"},"description":"Violation id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StagegateSnoozeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateDealPanelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Stagegate"],"summary":"Wake Stagegate Violation","description":"Wake a snoozed violation now: it returns to the queue and the board. The deal's owner only; personal key only.","operationId":"wake_stagegate_violation_stagegate_violations__violation_id__snooze_delete","parameters":[{"name":"violation_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Violation id (UUID).","title":"Violation Id"},"description":"Violation id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateDealPanelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"deals:delete","x-graph8-lifecycle":"active"}},"/stagegate/violations/{violation_id}/wrong":{"post":{"tags":["Stagegate"],"summary":"Mark Stagegate Violation Wrong","description":"Tell graph8 a violation is wrong, with an optional reason. One report per person; a repeat is a no-op. Personal key only.","operationId":"mark_stagegate_violation_wrong_stagegate_violations__violation_id__wrong_post","parameters":[{"name":"violation_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Violation id (UUID).","title":"Violation Id"},"description":"Violation id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/StagegateWrongRequest"},{"type":"null"}],"title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateFeedbackPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/stagegate/verdict-ratings":{"post":{"tags":["Stagegate"],"summary":"Rate Stagegate Verdict","description":"Thumbs up or down on a backtest verdict, for a saved rule (`rule_id`) or a draft (`conditions`). One rating per person; a changed thumb updates it. Personal key only.","operationId":"rate_stagegate_verdict_stagegate_verdict_ratings_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StagegateRatingRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateFeedbackPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/stagegate/rules/{rule_id}/backtest":{"post":{"tags":["Stagegate"],"summary":"Backtest Stagegate Rule","description":"Replay a saved rule over closed deals: did the deals it flags win less often? Changes nothing. 429 with `Retry-After` while every replay slot is busy.","operationId":"backtest_stagegate_rule_stagegate_rules__rule_id__backtest_post","parameters":[{"name":"rule_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Rule id (UUID).","title":"Rule Id"},"description":"Rule id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/StagegateBacktestRequest"},{"type":"null"}],"title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateBacktestPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/stagegate/backtest:preview":{"post":{"tags":["Stagegate"],"summary":"Preview Stagegate Backtest","description":"Backtest a DRAFT rule (conditions, optional pipelines) without saving it. Never cached; 429 with `Retry-After` while every replay slot is busy.","operationId":"preview_stagegate_backtest_stagegate_backtest_preview_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StagegateBacktestPreviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateBacktestPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/stagegate/backtest/rules":{"get":{"tags":["Stagegate"],"summary":"Rank Stagegate Rules By Gap","description":"Every rule ranked by how much worse the deals it flags do. With more than ten rules the verdicts are adjusted for multiple comparisons (`bh_applied`).","operationId":"rank_stagegate_rules_by_gap_stagegate_backtest_rules_get","parameters":[{"name":"window_days","in":"query","required":false,"schema":{"enum":[90,180,365],"type":"integer","description":"Closed deals from this many days back.","default":180,"title":"Window Days"},"description":"Closed deals from this many days back."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StagegateBacktestPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/contacts/tags":{"get":{"tags":["Contacts"],"summary":"List Contact Tags","description":"Org tag definitions with per-tag contact counts.","operationId":"list_contact_tags_contacts_tags_get","parameters":[{"name":"include_archived","in":"query","required":false,"schema":{"type":"boolean","description":"Include archived tags.","default":false,"title":"Include Archived"},"description":"Include archived tags."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContactTagListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"},"post":{"tags":["Contacts"],"summary":"Create Contact Tag","description":"Create a tag definition.","operationId":"create_contact_tag_contacts_tags_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContactTagCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContactTag_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/tags/{tag_id}":{"patch":{"tags":["Contacts"],"summary":"Update Contact Tag","description":"Rename, recolour, redescribe or archive a tag. Omitted fields stay.","operationId":"update_contact_tag_contacts_tags__tag_id__patch","parameters":[{"name":"tag_id","in":"path","required":true,"schema":{"type":"string","description":"Tag id.","title":"Tag Id"},"description":"Tag id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContactTagUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContactTag_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Contacts"],"summary":"Delete Contact Tag","description":"Delete a tag, optionally reassigning its contacts first.","operationId":"delete_contact_tag_contacts_tags__tag_id__delete","parameters":[{"name":"tag_id","in":"path","required":true,"schema":{"type":"string","description":"Tag id.","title":"Tag Id"},"description":"Tag id."},{"name":"reassign_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Move every assignment to this tag before deleting. Omit to drop the assignments with the tag.","title":"Reassign To"},"description":"Move every assignment to this tag before deleting. Omit to drop the assignments with the tag."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContactTagWriteResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"contacts:delete","x-graph8-lifecycle":"active"}},"/contacts/tags/merge":{"post":{"tags":["Contacts"],"summary":"Merge Contact Tags","description":"Fold one or more tags into a target. The sources are removed.\n\nNo shadowing risk against `/{tag_id}`: that path has no POST, so the\nliteral `merge` segment cannot be read as a tag id whatever the order.","operationId":"merge_contact_tags_contacts_tags_merge_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContactTagMergeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContactTagWriteResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/tags/assign":{"post":{"tags":["Contacts"],"summary":"Assign Contact Tags","description":"Add tags to contacts. Idempotent - re-assigning is not an error.","operationId":"assign_contact_tags_contacts_tags_assign_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContactTagAssignRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContactTagWriteResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/tags/unassign":{"post":{"tags":["Contacts"],"summary":"Unassign Contact Tags","description":"Remove tags from contacts. The tag definitions survive.","operationId":"unassign_contact_tags_contacts_tags_unassign_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContactTagAssignRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContactTagWriteResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts":{"get":{"tags":["Contacts"],"summary":"List Contacts","description":"List contacts with optional filtering and pagination.","operationId":"list_contacts_contacts_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (1-indexed)","default":1,"title":"Page"},"description":"Page number (1-indexed)"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page (max 200)","default":50,"title":"Limit"},"description":"Items per page (max 200)"},{"name":"email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by work email (exact match, case-insensitive; surrounding spaces ignored)","title":"Email"},"description":"Filter by work email (exact match, case-insensitive; surrounding spaces ignored)"},{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Filter by list ID","title":"List Id"},"description":"Filter by list ID"},{"name":"name","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by first or last name (partial match)","title":"Name"},"description":"Filter by first or last name (partial match)"},{"name":"job_title","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by job title (partial match)","title":"Job Title"},"description":"Filter by job title (partial match)"},{"name":"seniority_level","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by seniority level (exact match, case-insensitive). Spellings of the same level match each other: VP = Vice President; SVP/EVP = SVP = EVP = Senior/Executive Vice President; C-Suite = C-Level = CXO. `VP` (or `Vice President`) means VP and above, so it also returns the SVP/EVP band; `SVP/EVP` alone returns only that band. Pass several levels comma-separated to match any of them, e.g. `Director,VP`.","title":"Seniority Level"},"description":"Filter by seniority level (exact match, case-insensitive). Spellings of the same level match each other: VP = Vice President; SVP/EVP = SVP = EVP = Senior/Executive Vice President; C-Suite = C-Level = CXO. `VP` (or `Vice President`) means VP and above, so it also returns the SVP/EVP band; `SVP/EVP` alone returns only that band. Pass several levels comma-separated to match any of them, e.g. `Director,VP`."},{"name":"company_name","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by company name (partial match)","title":"Company Name"},"description":"Filter by company name (partial match)"},{"name":"company_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Filter by company ID","title":"Company Id"},"description":"Filter by company ID"},{"name":"country","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by country (exact match, case-insensitive; surrounding spaces ignored). Common aliases match each other: United States = US = USA; United Kingdom = UK.","title":"Country"},"description":"Filter by country (exact match, case-insensitive; surrounding spaces ignored). Common aliases match each other: United States = US = USA; United Kingdom = UK."},{"name":"state","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by state (exact match, case-insensitive; surrounding spaces ignored)","title":"State"},"description":"Filter by state (exact match, case-insensitive; surrounding spaces ignored)"},{"name":"city","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by city (partial match)","title":"City"},"description":"Filter by city (partial match)"},{"name":"job_department","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by job department (partial match)","title":"Job Department"},"description":"Filter by job department (partial match)"},{"name":"industry","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by company industry (partial match)","title":"Industry"},"description":"Filter by company industry (partial match)"},{"name":"include_custom_fields","in":"query","required":false,"schema":{"type":"boolean","description":"When true, each contact includes a `custom_fields` object of custom column values keyed by column slug. Default false keeps the legacy response shape and adds no extra query.","default":false,"title":"Include Custom Fields"},"description":"When true, each contact includes a `custom_fields` object of custom column values keyed by column slug. Default false keeps the legacy response shape and adds no extra query."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_ContactListItem__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"},"post":{"tags":["Contacts"],"summary":"Create Contacts","description":"Create a contact, optionally adding it to a list.\n\nThe contact is created independent of any list. When ``list_id`` is\nprovided, the contact is added to that list AFTER it is created; when\nomitted, the contact is created standalone. A company is resolved and\nattached from ``company_domain`` when supplied.\n\nDuplicate handling: when the submitted ``work_email`` / ``linkedin_url``\n(or the deterministic identity hash) already matches an existing contact,\nthe handler does NOT overwrite it — it writes nothing and skips the\n``list_id`` linkage. This endpoint mirrors the in-app create and responds\n``409 Conflict`` with the matched ``contact_id`` and a ``field_diff`` under\n``detail`` (rather than a misleading ``201`` success). The 409 is NOT\ncached under the ``Idempotency-Key``, so a later create of the same\nidentity is re-evaluated fresh. The 409 ``detail`` also carries ``hint``,\n``upsert`` and ``update``, which name the idempotent create-or-update route\n``PUT /contacts/assert`` and the ``PATCH /contacts/{id}`` for the matched\ncontact. To create-or-update in one call, use ``PUT /contacts/assert``.\n\nSupports optional Stripe-style idempotency via the ``Idempotency-Key``\nheader — a safe retry of the same key replays the first SUCCESSFUL response\n(flagged ``Idempotent-Replay: true``) rather than creating duplicate\ncontacts.","operationId":"create_contacts_contacts_post","parameters":[{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Optional. Retrying a create with the same key returns the first response instead of creating a duplicate (cached 24h). Omit for the existing non-idempotent behavior.","title":"Idempotency-Key"},"description":"Optional. Retrying a create with the same key returns the first response instead of creating a duplicate (cached 24h). Omit for the existing non-idempotent behavior."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContactCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContactCreateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/columns":{"get":{"tags":["Contacts"],"summary":"List Contact Columns","description":"List custom contact columns (table columns + global dynamic columns; +list-scoped if list_id given).","operationId":"list_contact_columns_contacts_columns_get","parameters":[{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Optional list ID. When provided, list-specific dynamic columns are included alongside global ones.","title":"List Id"},"description":"Optional list ID. When provided, list-specific dynamic columns are included alongside global ones."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_Column__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/contacts/columns/create":{"post":{"tags":["Contacts"],"summary":"Create Contact Column","description":"Create a custom contact column. Global if list_id is null, list-scoped otherwise.\n\nOptionally pass an `enrichment` block to provision a companion waterfall\npipeline in the same request — STRONGLY RECOMMENDED so the UI 'Enrich'\nbutton works out-of-the-box. Without it the column is created but isn't\nenrichable until a pipeline is provisioned via\nPOST /enrichment/waterfall/configs.","operationId":"create_contact_column_contacts_columns_create_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateContactColumnRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CreateContactColumnResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/columns/{column_id}":{"delete":{"tags":["Contacts"],"summary":"Delete Contact Column","description":"Soft-delete a custom contact column (sets deleted_at; data is not physically removed).","operationId":"delete_contact_column_contacts_columns__column_id__delete","parameters":[{"name":"column_id","in":"path","required":true,"schema":{"type":"integer","description":"ID of the column to delete","title":"Column Id"},"description":"ID of the column to delete"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"contacts:delete","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}":{"get":{"tags":["Contacts"],"summary":"Get Contact","description":"Get detailed information about a single contact.","operationId":"get_contact_contacts__contact_id__get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact ID","title":"Contact Id"},"description":"Contact ID"},{"name":"include_custom_fields","in":"query","required":false,"schema":{"type":"boolean","description":"When true, the response includes a `custom_fields` object of custom column values keyed by column slug. Default false omits it.","default":false,"title":"Include Custom Fields"},"description":"When true, the response includes a `custom_fields` object of custom column values keyed by column slug. Default false omits it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContactResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Contacts"],"summary":"Update Contact","description":"Update a contact's fields (partial update).\n\nCompany link (both optional; a contact may have no company): ``company_id``\nattaches an EXISTING company (mashup_companies.id) directly; ``company_domain``\nresolves-or-creates a company from its domain. ``company_id`` wins if both\nare given. Every other field is a plain column update. Provide any subset;\nat least one field (plain or company) is required.","operationId":"update_contact_contacts__contact_id__patch","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact ID","title":"Contact Id"},"description":"Contact ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContactUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Contacts"],"summary":"Delete Contact","description":"Soft-delete a contact.","operationId":"delete_contact_contacts__contact_id__delete","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact ID","title":"Contact Id"},"description":"Contact ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"contacts:delete","x-graph8-lifecycle":"active"}},"/companies":{"post":{"tags":["Companies"],"summary":"Create Company","description":"Create a company.\n\n``domain`` is required; the company is deduped by domain (an existing\ncompany with the same domain is reused rather than duplicated). Returns the\n``company_id`` (mashup_companies.id) — pass it to\n``g8_update_contact``/``company_id`` to attach the company to a contact, or\nuse it on a deal. Optionally add the company to a list via ``list_id``.\n\nRoutes to the same production ``CreateCompanyHandler`` the in-app \"add\ncompany\" flow uses (dedups, generates COMPANY_ID, creates the ABM/CRM\noverlay so the company is immediately pickable on a Deal).","operationId":"create_company_companies_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CompanyCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CompanyCreateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"},"get":{"tags":["Companies"],"summary":"List Companies","description":"List companies with optional filtering and pagination.","operationId":"list_companies_companies_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (1-indexed)","default":1,"title":"Page"},"description":"Page number (1-indexed)"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page (max 200)","default":50,"title":"Limit"},"description":"Items per page (max 200)"},{"name":"domain","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by domain (exact match)","title":"Domain"},"description":"Filter by domain (exact match)"},{"name":"industry","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by industry (partial match)","title":"Industry"},"description":"Filter by industry (partial match)"},{"name":"name","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by company name (partial match)","title":"Name"},"description":"Filter by company name (partial match)"},{"name":"employee_count_min","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":0},{"type":"null"}],"description":"Minimum employee count","title":"Employee Count Min"},"description":"Minimum employee count"},{"name":"employee_count_max","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":0},{"type":"null"}],"description":"Maximum employee count","title":"Employee Count Max"},"description":"Maximum employee count"},{"name":"country","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by country (exact match, case-insensitive; surrounding spaces ignored). Common aliases match each other: United States = US = USA; United Kingdom = UK.","title":"Country"},"description":"Filter by country (exact match, case-insensitive; surrounding spaces ignored). Common aliases match each other: United States = US = USA; United Kingdom = UK."},{"name":"state","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by state (exact match, case-insensitive; surrounding spaces ignored)","title":"State"},"description":"Filter by state (exact match, case-insensitive; surrounding spaces ignored)"},{"name":"city","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by city (partial match)","title":"City"},"description":"Filter by city (partial match)"},{"name":"description","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by company description (partial match)","title":"Description"},"description":"Filter by company description (partial match)"},{"name":"revenue_min","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":0},{"type":"null"}],"description":"Minimum annual revenue","title":"Revenue Min"},"description":"Minimum annual revenue"},{"name":"revenue_max","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":0},{"type":"null"}],"description":"Maximum annual revenue","title":"Revenue Max"},"description":"Maximum annual revenue"},{"name":"founded_year_min","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":1800},{"type":"null"}],"description":"Minimum founding year","title":"Founded Year Min"},"description":"Minimum founding year"},{"name":"founded_year_max","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","maximum":2100},{"type":"null"}],"description":"Maximum founding year","title":"Founded Year Max"},"description":"Maximum founding year"},{"name":"linkedin_followers_min","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":0},{"type":"null"}],"description":"Minimum LinkedIn followers","title":"Linkedin Followers Min"},"description":"Minimum LinkedIn followers"},{"name":"linkedin_followers_max","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":0},{"type":"null"}],"description":"Maximum LinkedIn followers","title":"Linkedin Followers Max"},"description":"Maximum LinkedIn followers"},{"name":"include_custom_fields","in":"query","required":false,"schema":{"type":"boolean","description":"When true, each company includes a `custom_fields` object of custom column values keyed by column slug. Default false keeps the legacy response shape and adds no extra query.","default":false,"title":"Include Custom Fields"},"description":"When true, each company includes a `custom_fields` object of custom column values keyed by column slug. Default false keeps the legacy response shape and adds no extra query."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_CompanyListItem__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/columns":{"get":{"tags":["Companies"],"summary":"List Company Columns","description":"List custom company columns (table columns + global dynamic columns; +list-scoped if list_id given).","operationId":"list_company_columns_companies_columns_get","parameters":[{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Optional list ID. When provided, list-specific dynamic columns are included alongside global ones.","title":"List Id"},"description":"Optional list ID. When provided, list-specific dynamic columns are included alongside global ones."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_Column__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/columns/create":{"post":{"tags":["Companies"],"summary":"Create Company Column","description":"Create a custom company column. Global if list_id is null, list-scoped otherwise.\n\nOptionally pass an `enrichment` block to provision a companion waterfall\npipeline in the same request — STRONGLY RECOMMENDED so the UI 'Enrich'\nbutton works out-of-the-box. Without it the column is created but isn't\nenrichable until a pipeline is provisioned via\nPOST /enrichment/waterfall/configs.","operationId":"create_company_column_companies_columns_create_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateCompanyColumnRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CreateCompanyColumnResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/companies/columns/{column_id}":{"delete":{"tags":["Companies"],"summary":"Delete Company Column","description":"Soft-delete a custom company column (sets deleted_at; data is not physically removed).","operationId":"delete_company_column_companies_columns__column_id__delete","parameters":[{"name":"column_id","in":"path","required":true,"schema":{"type":"integer","description":"ID of the column to delete","title":"Column Id"},"description":"ID of the column to delete"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"companies:delete","x-graph8-lifecycle":"active"}},"/companies/open-jobs":{"post":{"tags":["Companies"],"summary":"Get Companies Open Jobs","description":"What are these CRM companies hiring for, right now?\n\nA growth/buying signal: a company staffing up is a company with budget.\nUnrelated to `/marketplace/job-posts`, which publishes SDR roles you are\nrecruiting for - both are called \"jobs\" but they share no data.\n\n`company_ids` are `mashup_companies.id` values, NOT `linkedin_company_id`.\nBoth are bare ints, so passing the wrong one addresses a different company\nrather than erroring.\n\nResults split into `items` (resolved) and `unresolved`. An unresolved\ncompany is normal: it means the company could not be matched to a LinkedIn\ncompany page, not that it is not hiring. Read `lcid_confidence` before\ntrusting a match - 1.0 is an exact LinkedIn-URL match, 0.7 is a domain\nfallback that can mismatch on shared or parked domains. `open_jobs` counts\npostings seen within `window_days`; the source carries no open/closed state,\nso a filled role lingers until it ages out.\n\nOrg isolation is by Postgres schema, so ids belonging to another org come\nback as `unresolved` with no existence disclosure. Owner-level RBAC\n(`CompanyScopeFilter`) is deliberately not applied: it reads\n`user.permissions`, which an API-key user does not carry, so wiring it in\nwould resolve every API-key caller to scope \"none\" and return zero rows.","operationId":"get_companies_open_jobs_companies_open_jobs_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CompaniesOpenJobsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}":{"get":{"tags":["Companies"],"summary":"Get Company","description":"Get detailed information about a single company.","operationId":"get_company_companies__company_id__get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"Company ID","title":"Company Id"},"description":"Company ID"},{"name":"include_custom_fields","in":"query","required":false,"schema":{"type":"boolean","description":"When true, the response includes a `custom_fields` object of custom column values keyed by column slug. Default false omits it.","default":false,"title":"Include Custom Fields"},"description":"When true, the response includes a `custom_fields` object of custom column values keyed by column slug. Default false omits it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CompanyResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Companies"],"summary":"Update Company","description":"Update a company's fields (partial update).\n\nA ``name`` over 512 characters or a ``linkedin_url`` that is not a web\naddress is refused with a 400 and nothing is written. An employee_count\nwith no number, an unrecognised country, or a linkedin_url that is not on\nlinkedin.com is saved as sent and flagged in ``warnings`` (present only\nwhen there is something to flag).","operationId":"update_company_companies__company_id__patch","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"Company ID","title":"Company Id"},"description":"Company ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CompanyUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Companies"],"summary":"Delete Company","description":"Soft-delete a company.","operationId":"delete_company_companies__company_id__delete","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"Company ID","title":"Company Id"},"description":"Company ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"companies:delete","x-graph8-lifecycle":"active"}},"/companies/{company_id}/contacts":{"get":{"tags":["Companies"],"summary":"Get Company Contacts","description":"Get contacts belonging to a company.","operationId":"get_company_contacts_companies__company_id__contacts_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"Company ID","title":"Company Id"},"description":"Company ID"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page (max 200)","default":100,"title":"Limit"},"description":"Items per page (max 200)"},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Offset for pagination","default":0,"title":"Offset"},"description":"Offset for pagination"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_CompanyContactItem__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/lists/folders/assignments":{"put":{"tags":["Lists"],"summary":"Assign Lists To Folder","description":"File up to 500 lists into one folder, or out of every folder. FREE.\n\nAll or nothing: if ANY list is not visible to the key the whole call is a\n404 and nothing moves, so a caller cannot learn which ids exist by which\nones were filed. `folder_id` null unfiles them.","operationId":"assign_lists_to_folder_lists_folders_assignments_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ListFolderBulkAssignRequest"}}}},"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/lists/folders/assignments/{audience_id}":{"put":{"tags":["Lists"],"summary":"Assign List To Folder","description":"File one list into a folder, or out of every folder. FREE.\n\nRequires WRITE access to the list, as in the app. `folder_id` null unfiles\nit.","operationId":"assign_list_to_folder_lists_folders_assignments__audience_id__put","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","title":"Audience Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ListFolderAssignRequest"}}}},"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/lists/folders/stars/{audience_id}":{"put":{"tags":["Lists"],"summary":"Star List","description":"Star or unstar a list for this key. FREE.\n\nStarred ids come back in `GET /lists/folders` as `starred_ids`. A list the\nkey cannot see is a 404.","operationId":"star_list_lists_folders_stars__audience_id__put","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"The list (audience) id.","title":"Audience Id"},"description":"The list (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ListStarRequest"}}}},"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/lists/folders/activity/{audience_id}":{"post":{"tags":["Lists"],"summary":"Record List Opened","description":"Record that this key opened a list, for the \"recent\" shelf. FREE.\n\nRecents come back in `GET /lists/folders` as `recent_items`, most recent\nfirst. A list the key cannot see is a 404.","operationId":"record_list_opened_lists_folders_activity__audience_id__post","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"The list (audience) id.","title":"Audience Id"},"description":"The list (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/download":{"get":{"tags":["Lists"],"summary":"Download List","description":"Every row of a list as a CSV or XLSX file. FREE.\n\nUnbounded: the file holds the WHOLE list. CSV comes back as text; XLSX as\nbase64 in `content` with `encoding: \"base64\"`.","operationId":"download_list_lists__audience_id__download_get","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","title":"Audience Id"}},{"name":"format","in":"query","required":false,"schema":{"enum":["csv","xlsx"],"type":"string","description":"`csv` or `xlsx`.","default":"xlsx","title":"Format"},"description":"`csv` or `xlsx`."},{"name":"columns","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"string"}},{"type":"null"}],"description":"Only these columns. Omit for every column. LinkedIn profile URLs are always kept, as in the app.","title":"Columns"},"description":"Only these columns. Omit for every column. LinkedIn profile URLs are always kept, as in the app."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListDownloadPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/lists/folders":{"get":{"tags":["Lists"],"summary":"List List Folders","description":"Folders the key's org owns, plus org-visible folders owned by teammates.\n\n`assignments` maps list id -> folder id, which is what a rebuilt Lists\nscreen needs to place each list without a second round trip.\n\nThe internal `list_folders` takes TWO different scope classes: a\ncampaign_builder `service_scope` (carrying `.is_scoped`/`.allowed_list_ids`)\nand an audiences `visibility_scope`. They are resolved by distinct\ndependencies - passing one object as both raises AttributeError -> 500.","operationId":"list_list_folders_lists_folders_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListFolderIndexResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"},"post":{"tags":["Lists"],"summary":"Create List Folder","description":"Create a folder. Titles are de-duplicated per owner by the same\ninternal path the app uses, so a repeat title returns its 409 unchanged.","operationId":"create_list_folder_lists_folders_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ListFolderCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListFolderResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/lists/folders/{folder_id}":{"patch":{"tags":["Lists"],"summary":"Update List Folder","description":"Rename a folder or change its visibility. Omitted fields are untouched.","operationId":"update_list_folder_lists_folders__folder_id__patch","parameters":[{"name":"folder_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Folder id.","title":"Folder Id"},"description":"Folder id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ListFolderUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListFolderResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Lists"],"summary":"Delete List Folder","description":"Delete a folder. The lists inside it are NOT deleted - they are\nunfiled, exactly as in the app.","operationId":"delete_list_folder_lists_folders__folder_id__delete","parameters":[{"name":"folder_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Folder id.","title":"Folder Id"},"description":"Folder id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/lists/performance":{"get":{"tags":["Lists"],"summary":"Get List Performance","description":"Engagement counters for one list or every list the key may see.","operationId":"get_list_performance_lists_performance_get","parameters":[{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Filter to a single list. Omit for all lists.","title":"List Id"},"description":"Filter to a single list. Omit for all lists."},{"name":"days","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":1},{"type":"null"}],"description":"Restrict sends/events to the last N days. Omit for all-time. Ignored when start_date and end_date are both supplied.","title":"Days"},"description":"Restrict sends/events to the last N days. Omit for all-time. Ignored when start_date and end_date are both supplied."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Inclusive start of an anchored range, `YYYY-MM-DD`. Requires end_date.","title":"Start Date"},"description":"Inclusive start of an anchored range, `YYYY-MM-DD`. Requires end_date."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Inclusive end of an anchored range, `YYYY-MM-DD`.","title":"End Date"},"description":"Inclusive end of an anchored range, `YYYY-MM-DD`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListPerformanceResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/lists":{"get":{"tags":["Lists"],"summary":"List Lists","description":"List all lists (audiences) in the organization, optionally filtered by title.","operationId":"list_lists_lists_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (1-indexed)","default":1,"title":"Page"},"description":"Page number (1-indexed)"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page (max 200)","default":50,"title":"Limit"},"description":"Items per page (max 200)"},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"description":"Case-insensitive substring match on the list title. Omit for every list.","title":"Search"},"description":"Case-insensitive substring match on the list title. Omit for every list."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_ListResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"},"post":{"tags":["Lists"],"summary":"Create List","description":"Create a new empty list.","operationId":"create_list_lists_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ListCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListCreateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/lists/{list_id}":{"patch":{"tags":["Lists"],"summary":"Update List","description":"Update a list's name and/or its agent-readable description (#16641).","operationId":"update_list_lists__list_id__patch","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","description":"List ID","title":"List Id"},"description":"List ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ListUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Lists"],"summary":"Delete List","description":"Soft-delete a list.","operationId":"delete_list_lists__list_id__delete","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","description":"List ID","title":"List Id"},"description":"List ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/lists/{list_id}/contacts":{"get":{"tags":["Lists"],"summary":"Get List Contacts","description":"Get contacts in a specific list.","operationId":"get_list_contacts_lists__list_id__contacts_get","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","description":"List ID","title":"List Id"},"description":"List ID"},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (1-indexed)","default":1,"title":"Page"},"description":"Page number (1-indexed)"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page (max 200)","default":50,"title":"Limit"},"description":"Items per page (max 200)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_ContactListItem__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"},"post":{"tags":["Lists"],"summary":"Add Contacts To List","description":"Add contacts to a list by their IDs.\n\n``added`` is the number of membership rows really created. Ids that are not\nlive contacts in this org come back in ``not_found``; ids already on the\nlist in ``already_member`` (LI-01). A missing or deleted list is a 404.","operationId":"add_contacts_to_list_lists__list_id__contacts_post","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","description":"List ID","title":"List Id"},"description":"List ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AddContactsToListRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Lists"],"summary":"Remove Contacts From List","description":"Remove contacts from a list.\n\n``removed`` is the number of membership rows really deleted; requested ids\nthat were not on the list come back in ``not_member`` (LI-01). A missing or\ndeleted list is a 404 (a deleted list's membership is frozen, so nothing\ncould be removed from it anyway).","operationId":"remove_contacts_from_list_lists__list_id__contacts_delete","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","description":"List ID","title":"List Id"},"description":"List ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RemoveContactsFromListRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/companies":{"delete":{"tags":["Lists"],"summary":"Delete Companies From List","description":"Remove companies from a list.","operationId":"delete_companies_from_list_lists__audience_id__companies_delete","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"agFilterModel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"AgGrid filter JSON. Every company in the list matching it is removed, IN ADDITION to `company_ids` - the two combine rather than the filter narrowing the ids.","title":"Agfiltermodel"},"description":"AgGrid filter JSON. Every company in the list matching it is removed, IN ADDITION to `company_ids` - the two combine rather than the filter narrowing the ids."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeleteCompaniesFromListRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/suppressions":{"delete":{"tags":["Lists"],"summary":"Delete Suppressions From List","description":"Remove suppressions from a suppression list.\n\nRemoving a suppression makes those people CONTACTABLE again - this is the\none removal here that changes who can be emailed.","operationId":"delete_suppressions_from_list_lists__audience_id__suppressions_delete","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeleteSuppressionsFromListRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/leads":{"delete":{"tags":["Lists"],"summary":"Delete Leads From List","description":"Remove leads from a list.","operationId":"delete_leads_from_list_lists__audience_id__leads_delete","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeleteLeadsFromListRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/deals":{"post":{"tags":["Lists"],"summary":"Add Deals To List","description":"Put deals on a deals list.\n\nEach deal is checked against the caller's DEAL scope as well as the list's,\nso adding a deal you cannot see is refused rather than silently skipped.","operationId":"add_deals_to_list_lists__audience_id__deals_post","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AddDealsToListRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/lists/create-empty":{"post":{"tags":["Lists"],"summary":"Create Empty List","description":"Create a list with nothing in it, to fill later.\n\nSEND AN `idempotency_key`. Without one a retried request makes a second\nempty list, and a duplicate list is harder to notice than a failed call.","operationId":"create_empty_list_lists_create_empty_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateEmptyListRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/refresh":{"post":{"tags":["Lists"],"summary":"Refresh Dynamic List","description":"Re-run a dynamic list's query now.\n\nMembership can go DOWN as well as up: a record that no longer matches\nleaves. Only meaningful for a list created with `is_dynamic`.","operationId":"refresh_dynamic_list_lists__audience_id__refresh_post","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/owner/preview":{"get":{"tags":["Lists"],"summary":"Preview List Owner Transfer","description":"What a transfer WOULD do, before doing it. Changes nothing.\n\nWorth calling first: `list_and_records` re-owns every record in the list,\nwhich can change who else can see them, and this says how many before you\ncommit.","operationId":"preview_list_owner_transfer_lists__audience_id__owner_preview_get","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"new_owner_user_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"description":"Candidate owner's PropelAuth user id.","title":"New Owner User Id"},"description":"Candidate owner's PropelAuth user id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/owner":{"patch":{"tags":["Lists"],"summary":"Reassign List Owner","description":"Hand a list to someone else.\n\n`mode=\"list_and_records\"` ALSO re-owns every record in the list. Under\nrecord-level scoping that changes who can see them, so preview it first.\n\nThis route carries no `verify_list_access_dep` in the app - the transfer\nrules are enforced inside the handler instead, and they are stricter than\nthe per-list read gate rather than weaker.","operationId":"reassign_list_owner_lists__audience_id__owner_patch","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ReassignListOwnerRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/column-capabilities":{"get":{"tags":["Lists"],"summary":"Get List Column Capabilities","description":"Which dynamic columns this list can carry, and what may be written.\n\nRead this before `PATCH /dynamic-value`: a column that is not writable\nhere is refused there, and the capability map is the only way to know\nwhich is which without guessing.","operationId":"get_list_column_capabilities_lists__audience_id__column_capabilities_get","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"object_type","in":"query","required":true,"schema":{"enum":["mashup_contacts","mashup_companies"],"type":"string","description":"Which grid's columns: contacts or companies.","title":"Object Type"},"description":"Which grid's columns: contacts or companies."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/keyword-links":{"get":{"tags":["Lists"],"summary":"Get List Keyword Links","description":"Which intent keywords auto-populate this list.\n\nThe authoritative source: the link lives in\n`cb_keyword_sync_configs.list_id`, not in the list's own query, so a list\ncan be fed by a keyword while its `icp_query` says nothing about it.","operationId":"get_list_keyword_links_lists__audience_id__keyword_links_get","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/dynamic-value":{"patch":{"tags":["Lists"],"summary":"Patch Dynamic Value","description":"Write ONE cell of a user-owned dynamic column.\n\nFail-closed: a protected, unknown, other-list or other-org destination is\nrefused rather than written somewhere plausible.\n\nSend `expected_value` to make the write conditional on the cell not having\nmoved. Omit it and the write wins unconditionally, which on a shared grid\nmeans overwriting a colleague's edit without knowing.","operationId":"patch_dynamic_value_lists__audience_id__dynamic_value_patch","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PatchDynamicValueRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/tracked-links/columns":{"get":{"tags":["Lists"],"summary":"Get Tracked Link Columns","description":"Which of this list's columns can be interpolated into a tracked link.\n\nThe source of the names usable in `params_template` - anything else\nresolves to nothing and produces a link with an empty parameter.","operationId":"get_tracked_link_columns_lists__audience_id__tracked_links_columns_get","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/generate-tracked-links":{"post":{"tags":["Lists"],"summary":"Generate Tracked Links","description":"Mint one tracked URL per row, into a column on the list.\n\n`params_template` interpolates this list's own columns - check\n`GET /tracked-links/columns` first, because an unresolvable name produces\na link with an empty parameter rather than an error.\n\n`placement` only applies when `shorten` is off.","operationId":"generate_tracked_links_lists__audience_id__generate_tracked_links_post","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/GenerateTrackedLinksRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/lists/masters":{"get":{"tags":["Lists"],"summary":"List Master Lists","description":"Master lists: the ones that union other lists and stay in sync.","operationId":"list_master_lists_lists_masters_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"},"post":{"tags":["Lists"],"summary":"Create Master List","description":"Create a master list from other lists.\n\n`include_all_sources` takes EVERY list of this type, including ones\ncreated later - a standing rule rather than a snapshot, and it makes\n`source_list_ids` irrelevant.\n\nThe first sync runs in the BACKGROUND, so the list comes back empty and\nfills shortly after.","operationId":"create_master_list_lists_masters_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateMasterListRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/master-config":{"patch":{"tags":["Lists"],"summary":"Update Master List Config","description":"Replace a master list's sources.\n\nA REPLACE, not a merge: a source you omit stops feeding the list. The\nconfig is saved synchronously and the re-sync runs afterwards, so a 200\nmeans the config is stored, not that membership has caught up.","operationId":"update_master_list_config_lists__audience_id__master_config_patch","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateMasterListConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/master-refresh":{"post":{"tags":["Lists"],"summary":"Refresh Master List Now","description":"Re-sync a master list from its sources now. Returns add/remove counts.","operationId":"refresh_master_list_now_lists__audience_id__master_refresh_post","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/usage":{"get":{"tags":["Lists"],"summary":"Get List Usage","description":"Count the live campaigns, sequences, newsletters and master lists that use this list.\n\nCall it before deleting a list so you can state the real blast radius.\nRead-only. The list must be visible to the key (404 otherwise).","operationId":"get_list_usage_lists__audience_id__usage_get","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/master-config/preview":{"post":{"tags":["Lists"],"summary":"Preview Master List Config","description":"Dry run of `PATCH /lists/{audience_id}/master-config`.\n\nReturns how many members saving the proposed sources would add and remove.\nWrites nothing and spends nothing. Admin only, like the write it previews.","operationId":"preview_master_list_config_lists__audience_id__master_config_preview_post","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateMasterListConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/lists/timeline/outcomes":{"get":{"tags":["Lists"],"summary":"Get Org Spend Outcomes","description":"What happened to the deals on contacts credits were spent on, across the organisation.\n\nTotals count each deal once over the contacts the key may see; the list and\ncontact rankings hold only lists and contacts the key may open. Read-only.","operationId":"get_org_spend_outcomes_lists_timeline_outcomes_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/timeline":{"get":{"tags":["Lists"],"summary":"Get List Timeline","description":"The funnel timeline for one list: each step's count, credits spent and outcome.\n\nEvery step is present in a fixed order; `count` and `cost_credits` are\n`null` when not recorded, which is not `0`. Read-only. 404 when the list is\nnot visible to the key, 422 for a companies list, 504 on a slow read.","operationId":"get_list_timeline_lists__audience_id__timeline_get","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/lists/{audience_id}/timeline/steps/{step_id}/contacts":{"get":{"tags":["Lists"],"summary":"Get List Timeline Step Contacts","description":"One keyset-paginated page of the contacts behind a single timeline step.\n\nRows are limited to contacts the key may see, in the page query itself, so\n`total` and `next_cursor` describe the same visible population. Steps that\nhave no per-contact drilldown answer 422 with a reason. Read-only.","operationId":"get_list_timeline_step_contacts_lists__audience_id__timeline_steps__step_id__contacts_get","parameters":[{"name":"audience_id","in":"path","required":true,"schema":{"type":"integer","description":"List (audience) id.","title":"Audience Id"},"description":"List (audience) id."},{"name":"step_id","in":"path","required":true,"schema":{"type":"string","description":"One of the pinned timeline step kinds returned by the list timeline.","title":"Step Id"},"description":"One of the pinned timeline step kinds returned by the list timeline."},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Opaque cursor from a prior page's `next_cursor`.","title":"Cursor"},"description":"Opaque cursor from a prior page's `next_cursor`."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Page size.","default":50,"title":"Limit"},"description":"Page size."},{"name":"call_source","in":"query","required":false,"schema":{"type":"string","pattern":"^(list|manual)$","description":"`dial`/`connected` steps only: this list's dialer-session calls, or calls made manually.","default":"list","title":"Call Source"},"description":"`dial`/`connected` steps only: this list's dialer-session calls, or calls made manually."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/lists/{list_id}/data-columns":{"get":{"tags":["Lists"],"summary":"List Data Columns","description":"The enrichment (waterfall), AI and dynamic columns this list carries.\n\nPass a row's `column_name_db` in `extra_fields` on `POST .../integrity-check`.","operationId":"list_data_columns_lists__list_id__data_columns_get","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"List (audience) id.","title":"List Id"},"description":"List (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/lists/{list_id}/integrity-check":{"post":{"tags":["Lists"],"summary":"Check List Integrity","description":"How complete the list's data is: per field, how many contacts have a usable value.\n\nCovers the default contact fields (email, phone, name, company, ...) plus any\n`extra_fields` named. Reads only; nothing is written or enriched.","operationId":"check_list_integrity_lists__list_id__integrity_check_post","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"List (audience) id.","title":"List Id"},"description":"List (audience) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/IntegrityCheckRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/imports":{"post":{"tags":["Imports"],"summary":"Upload Import File","description":"Upload a CSV or Excel file and get back its id and row count.\n\nNothing is imported by this call - the file is stored and parsed so it can\nbe previewed and then imported. The 25 MB ceiling is the app's, enforced by\nreading one byte past it so an exact-boundary file is distinguishable from\nan oversized one even when `Content-Length` is missing or dishonest.\n\nThe `row_count` that comes back is what the import pre-check budgets\nagainst: it is treated as the upper bound on NEW contacts, so an import is\nrefused if that many would breach the org's limit, even though some rows\nwill resolve to updates.","operationId":"upload_import_file_imports_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_import_file_imports_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DataFileUploadResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/imports/{import_id}/preview":{"post":{"tags":["Imports"],"summary":"Preview Import File","description":"See how the file will be read, with a mapping applied. Writes nothing.","operationId":"preview_import_file_imports__import_id__preview_post","parameters":[{"name":"import_id","in":"path","required":true,"schema":{"type":"string","description":"Id returned by the upload.","title":"Import Id"},"description":"Id returned by the upload."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":10,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"type":"object","additionalProperties":{"type":"string"},"description":"Source column -> graph8 field, the same mapping you intend to import with. Send it HERE: an unmapped column the importer cannot recognise is dropped SILENTLY, and this is the only way to see that before writing to a customer's CRM.","title":"Column Mapping"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DataFilePreviewResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/imports/{import_id}/check-duplicates":{"post":{"tags":["Imports"],"summary":"Check Import Duplicates","description":"Count how many rows of an uploaded file already exist, before importing. Writes nothing.\n\nContacts are matched by work email, companies by domain. The response\ncarries the counts and, for a sample of matched rows, YOUR OWN file row\n(`csv_data`) with `matched: true`. It never returns the existing record:\nthe app handler matches across the whole organisation with no record\nscope, so returning its `existing` details would let a key whose contact\nvisibility is own/team look up the identity behind any email. Use the\ncontact and company reads for the record itself, which are scope-gated.\n\nNeeds `contacts:read` (entity_type `contact`) or `companies:read`\n(`company`) as well as `lists:read`. The file must belong to the key's\norganisation (the load is org-scoped).","operationId":"check_import_duplicates_imports__import_id__check_duplicates_post","parameters":[{"name":"import_id","in":"path","required":true,"schema":{"type":"string","description":"Id returned by the upload.","title":"Import Id"},"description":"Id returned by the upload."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CheckImportDuplicatesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/imports/{import_id}/contacts":{"post":{"tags":["Imports"],"summary":"Import Contacts","description":"Import the file's rows as contacts into a list. THIS WRITES REAL RECORDS.\n\nTwo separate authorisations, both resolved for the key's principal and both\nrequired - neither implies the other:\n\n  * may this caller CREATE contacts at all (`enforce_object_create`);\n  * may they WRITE to this particular list (`verify_list_access`).\n\n`update_policy` defaults to `override`: a row matching an existing contact\nREPLACES that contact's fields rather than only filling blanks. Send\n`autofill` if the file should not win over what is already there.","operationId":"import_contacts_imports__import_id__contacts_post","parameters":[{"name":"import_id","in":"path","required":true,"schema":{"type":"string","description":"Id returned by the upload.","title":"Import Id"},"description":"Id returned by the upload."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ImportContactsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ImportContactsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/mailboxes/schedule-buy/suggest":{"post":{"tags":["Schedule Buy"],"summary":"Suggest Plan","description":"Size a plan before you lock it. SPENDS NOTHING, holds nothing.\n\nCounts the idle mailboxes you already have, then works out how many new\ndomains and mailboxes the target volume still needs and what they would\ncost in credits. Pass its idle count back as `idle_mailboxes_snapshot`\nwhen you lock the plan.","operationId":"suggest_plan_mailboxes_schedule_buy_suggest_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ScheduleBuySuggestRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/mailboxes/schedule-buy/suggest-domains":{"post":{"tags":["Schedule Buy"],"summary":"Suggest Plan Domains","description":"Candidate domain names a plan WOULD buy. SPENDS NOTHING, buys nothing.\n\nSame generator, same owned-domain exclusion and same live availability\nprobe the executor uses at buy time, so the preview is honest rather than\ndecorative.\n\n`offset` rotates the generator: call again with a higher offset to get a\nfresh set instead of the same list. `avoid` excludes names you have\nalready rejected.","operationId":"suggest_plan_domains_mailboxes_schedule_buy_suggest_domains_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ScheduleBuyDomainSuggestRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/mailboxes/schedule-buy/check-domains":{"post":{"tags":["Schedule Buy"],"summary":"Check Plan Domains","description":"Validate names you edited: already yours, available, or refused. SPENDS NOTHING.\n\nOne entry per name. `available: null` means the probe itself failed and\nthe answer is UNKNOWN - not that the name is taken. Treat null as \"check\nagain\" rather than as a no.","operationId":"check_plan_domains_mailboxes_schedule_buy_check_domains_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ScheduleBuyDomainCheckRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/mailboxes/schedule-buy/plans":{"post":{"tags":["Schedule Buy"],"summary":"Create Plan","description":"Create and LOCK a buying plan. PLACES REAL CREDIT HOLDS IMMEDIATELY.\n\nLocking reserves credits for the WHOLE plan up front - one hold per batch,\nup to two hundred of them - even though the domains are bought a batch a\nday afterwards. The credits are gone from your spendable balance the\nmoment this returns. `total_credits_held` in the response is the figure.\n\nOrg admins and owners only, and only for an org on a paid or pre-funded\nplan. 402 if the balance cannot cover the plan, 429 if the org has locked\nmore than five plans this hour, 400 for an unsupported extension or an\nempty plan. With `reuse_domains`, 409 when a domain's mailbox count changed\n(or it filled up) while the plan was locking: nothing stays held, re-read\nthe domains and lock again.\n\nAt least one `persona_ids` entry is required. Manual `registrants` /\n`mailbox_aliases` are not accepted for new plans. `idle_mailboxes_snapshot`\nis your own count, used to detect drift - the server recomputes it and\nreturns its own as `server_idle_mailboxes`.\n\nSend an `Idempotency-Key` header. A retried lock without one places a\nsecond full set of holds.","operationId":"create_plan_mailboxes_schedule_buy_plans_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ScheduleBuyPlanRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"},"get":{"tags":["Schedule Buy"],"summary":"List Plans","description":"The org's plans, newest first, with live progress on each.\n\n`mailboxes_provisioned` and `landing_pages_hosted` are best-effort\ndecoration: a failure computing them reports zero rather than failing the\nlist, so do not read a zero as \"nothing has been provisioned\".","operationId":"list_plans_mailboxes_schedule_buy_plans_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/mailboxes/schedule-buy/plans/{plan_id}":{"get":{"tags":["Schedule Buy"],"summary":"Get Plan","description":"One plan and every batch it has run, in order.\n\nA batch carries what it bought and what it was charged. The internal\ncredit-ledger transaction ids are deliberately not published - use\n`GET /usage` for the ledger.","operationId":"get_plan_mailboxes_schedule_buy_plans__plan_id__get","parameters":[{"name":"plan_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Schedule Buy plan id - from GET /mailboxes/schedule-buy/plans","title":"Plan Id"},"description":"Schedule Buy plan id - from GET /mailboxes/schedule-buy/plans"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Schedule Buy"],"summary":"Cancel Plan","description":"Cancel a plan and release every hold it has not yet spent. NOT REVERSIBLE.\n\nBatches already bought stay bought - this stops the plan buying MORE. The\nreleased credits return to the org's balance; there is no un-cancel, so a\nplan you want to stop temporarily is a different operation.\n\nOrg admins and owners only. 409 if the plan is executing a batch right now\n(retry in a few minutes - cancelling mid-batch could release a hold the\nexecutor is about to charge) or if the plan is in a state that cannot be\ncancelled at all.","operationId":"cancel_plan_mailboxes_schedule_buy_plans__plan_id__delete","parameters":[{"name":"plan_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Schedule Buy plan id - from GET /mailboxes/schedule-buy/plans","title":"Plan Id"},"description":"Schedule Buy plan id - from GET /mailboxes/schedule-buy/plans"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/mailboxes/schedule-buy/plans/{plan_id}/pause":{"post":{"tags":["Schedule Buy"],"summary":"Pause Plan","description":"Pause a plan: the daily executor skips it and buys nothing more.\n\nEvery credit hold stays RESERVED - pausing does not release money, it only\nstops it being spent. Resume picks up exactly where it left off. Org admins\nand owners only; 409 if the plan is not in a pausable state.","operationId":"pause_plan_mailboxes_schedule_buy_plans__plan_id__pause_post","parameters":[{"name":"plan_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Schedule Buy plan id - from GET /mailboxes/schedule-buy/plans","title":"Plan Id"},"description":"Schedule Buy plan id - from GET /mailboxes/schedule-buy/plans"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/mailboxes/schedule-buy/plans/{plan_id}/resume":{"post":{"tags":["Schedule Buy"],"summary":"Resume Plan","description":"Resume a paused plan. BUYING RESTARTS on the next daily tick.\n\nThe plan goes back to in-progress and its held credits start being charged\nagain, batch by batch, catching up first. Org admins and owners only; 409\nunless the plan is paused.","operationId":"resume_plan_mailboxes_schedule_buy_plans__plan_id__resume_post","parameters":[{"name":"plan_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Schedule Buy plan id - from GET /mailboxes/schedule-buy/plans","title":"Plan Id"},"description":"Schedule Buy plan id - from GET /mailboxes/schedule-buy/plans"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/mailboxes/schedule-buy/eligible-domains":{"get":{"tags":["Schedule Buy"],"summary":"List Eligible Domains","description":"The organisation's domains a REUSE plan would adopt. SPENDS NOTHING.\n\nOwned, live, usable, transfer-free, with FEWER live mailboxes than `mailboxes_per_domain` (partly filled domains are\ntopped up), not already claimed by another active plan, and connected to the mail service when sourced externally.\nEach row carries `existing_mailboxes` and `missing_mailboxes`. It is the same predicate the lock enforces, so the list\ncannot disagree with a lock. Capped at the lock's own limit (500); `truncated` says the organisation owns more.","operationId":"list_eligible_domains_mailboxes_schedule_buy_eligible_domains_get","parameters":[{"name":"mailboxes_per_domain","in":"query","required":false,"schema":{"type":"integer","maximum":5,"minimum":1,"description":"The plan's mailboxes per domain; a domain qualifies while it has fewer live mailboxes.","default":3,"title":"Mailboxes Per Domain"},"description":"The plan's mailboxes per domain; a domain qualifies while it has fewer live mailboxes."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/mailboxes/schedule-buy/plans/{plan_id}/batches":{"get":{"tags":["Schedule Buy"],"summary":"List Plan Batches","description":"One page of a plan's batch history, oldest batch first. SPENDS NOTHING. 404 for a plan that is not the organisation's.","operationId":"list_plan_batches_mailboxes_schedule_buy_plans__plan_id__batches_get","parameters":[{"name":"plan_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Schedule Buy plan id - from GET /mailboxes/schedule-buy/plans","title":"Plan Id"},"description":"Schedule Buy plan id - from GET /mailboxes/schedule-buy/plans"},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"1-based page index.","default":1,"title":"Page"},"description":"1-based page index."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Rows per page.","default":50,"title":"Limit"},"description":"Rows per page."},{"name":"return_total","in":"query","required":false,"schema":{"type":"boolean","description":"Include a real COUNT over the matching set.","default":true,"title":"Return Total"},"description":"Include a real COUNT over the matching set."},{"name":"agFilterModel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"AG Grid filterModel JSON.","title":"Agfiltermodel"},"description":"AG Grid filterModel JSON."},{"name":"agSortModel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"AG Grid sortModel JSON.","title":"Agsortmodel"},"description":"AG Grid sortModel JSON."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/mailboxes/schedule-buy/plans/{plan_id}/personas":{"post":{"tags":["Schedule Buy"],"summary":"Add Plan Personas","description":"ADD personas to a persona-mode plan. Org admin only. Add-only: a persona is never detached from a live plan.\n\n409 for a finished plan (completed, cancelled or draft) and for a MANUAL-alias plan, which has no personas to extend.\nThe mailboxes a persona already got stay attributed to it. Spends nothing.","operationId":"add_plan_personas_mailboxes_schedule_buy_plans__plan_id__personas_post","parameters":[{"name":"plan_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Schedule Buy plan id - from GET /mailboxes/schedule-buy/plans","title":"Plan Id"},"description":"Schedule Buy plan id - from GET /mailboxes/schedule-buy/plans"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SchedulePlanPersonasRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/mailboxes/available-tags":{"get":{"tags":["Mailboxes"],"summary":"List Available Mailbox Tags","description":"Every tag on the organisation's mailboxes: `tags`, and the same split into `system_tags` and `sender_tags`.","operationId":"list_available_mailbox_tags_mailboxes_available_tags_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxOverviewPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/provider-domains/stats/mailbox-breakdown":{"get":{"tags":["Mailboxes"],"summary":"Get Mailbox Breakdown","description":"The capacity-weighted partition of live mailboxes: allocation, sender, health, tag, blocklist, sequence, capacity.\n\nAllocation precedence is unavailable, then in sequences, then free. `sequences` lists every named sequence slice. Every\nsource read is fail-soft, so a source that is down leaves its facet empty rather than failing the read.","operationId":"get_mailbox_breakdown_provider_domains_stats_mailbox_breakdown_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxOverviewPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/mailboxes/{mailbox_id}/request-cancellation":{"post":{"tags":["Mailboxes"],"summary":"Request Mailbox Cancellation","description":"Stop paying for a purchased mailbox. STOPS SPEND; eventually destroys it.\n\nTwo steps, and this is the first: the mailbox is scheduled for\ncancellation at the provider and keeps working until its current period\nends. A poller then flips it to cancelled, after which\n`DELETE /mailboxes/{mailbox_id}` removes graph8's record of it.\n\nReversible with `POST /mailboxes/uncancel` while it is still scheduled -\nwhich resumes billing.\n\n422 for a mailbox that was not purchased through graph8, or one already in\nthe cancellation flow. 502 if the provider refused - read that as \"nothing\nwas cancelled\", not as a partial success.\n\nNeeds a personal API key whose user holds a mailbox write permission.","operationId":"request_mailbox_cancellation_mailboxes__mailbox_id__request_cancellation_post","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Mailbox id (mailboxes.id)","title":"Mailbox Id"},"description":"Mailbox id (mailboxes.id)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/mailboxes/uncancel":{"post":{"tags":["Mailboxes"],"summary":"Uncancel Mailboxes","description":"Undo a scheduled cancellation. RESUMES BILLING on every mailbox listed.\n\nBulk by design; pass one id for a single undo. Idempotent - a mailbox that\nis already active is a no-op success rather than an error.\n\nRead the per-id breakdown in `results`, not the HTTP status: a mailbox\nthat could not be restored is REPORTED, and the request still returns 200\nwith the ones that were.\n\n422 for an org without an active or pre-funded plan. A churned org must\nnot resume mailbox billing, and restoring one would be re-cancelled within\ndays anyway.\n\nNeeds a personal API key whose user holds a mailbox write permission.","operationId":"uncancel_mailboxes_mailboxes_uncancel_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MailboxUncancelRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/mailboxes/{mailbox_id}/share":{"post":{"tags":["Mailboxes"],"summary":"Share Mailbox","description":"Let the rest of the org send from this mailbox, or stop letting them.\n\nSharing hands over a sending CREDENTIAL, not a view: anyone in the org can\nthen attach it to their own sequences. Explicit rather than a toggle, so a\nretried request cannot silently flip it back.\n\nOwner-only (plus org admins and owners) - sharing is the one mailbox\nmutation a team-mate the mailbox is already shared with cannot perform.\nNeeds a personal API key.","operationId":"share_mailbox_mailboxes__mailbox_id__share_post","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Mailbox id (mailboxes.id)","title":"Mailbox Id"},"description":"Mailbox id (mailboxes.id)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MailboxShareRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/mailboxes/{mailbox_id}/archive":{"post":{"tags":["Mailboxes"],"summary":"Archive Mailbox","description":"Archive a mailbox, or restore it. Explicit rather than a toggle.\n\nArchiving hides the mailbox from pickers so nothing new is attached to it;\nit is not deleted, keeps its history, and `is_archived=false` brings it\nback. It does not cancel a purchased mailbox's billing - that is\n`request-cancellation`.\n\nNeeds a personal API key whose user holds a mailbox write permission.","operationId":"archive_mailbox_mailboxes__mailbox_id__archive_post","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Mailbox id (mailboxes.id)","title":"Mailbox Id"},"description":"Mailbox id (mailboxes.id)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MailboxArchiveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/mailboxes/bulk-import":{"post":{"tags":["Mailboxes"],"summary":"Bulk Import Mailboxes","description":"Connect many mailboxes you already own, from CSV. Buys nothing.\n\n202 means ACCEPTED, not imported: the work runs in the background and the\nresponse carries no per-row outcome. Poll `GET /mailboxes` to see what\nlanded, and expect rows to appear gradually rather than all at once.\n\nCredentials in the CSV are write-only - stored encrypted and never\nreturned by this or any other endpoint.","operationId":"bulk_import_mailboxes_mailboxes_bulk_import_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MailboxBulkImportRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/mailboxes/{mailbox_id}/health/placement-test":{"post":{"tags":["Mailboxes"],"summary":"Run Mailbox Placement Test","description":"Run an inbox-placement test for ONE mailbox. THIS CHARGES CREDITS.\n\nSame charging path as `POST /placement/tests`: credits are held and\ncharged when the test is CREATED, not when it completes. Call\n`POST /placement/tests/estimate` first if you want the figure - that one\nis free.\n\nOne test per mailbox per 72 hours; a call inside the window is a 429\ncarrying `cooldown_until`. The test itself completes asynchronously - read\nit back with `GET /placement/tests/{test_id}`.\n\nOrg admins and owners only, enforced by the handler itself.","operationId":"run_mailbox_placement_test_mailboxes__mailbox_id__health_placement_test_post","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Mailbox id (mailboxes.id)","title":"Mailbox Id"},"description":"Mailbox id (mailboxes.id)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/warmup/{mailbox_id}":{"delete":{"tags":["Mailboxes"],"summary":"Delete Warmup","description":"Remove this mailbox's warmup account entirely. NOT REVERSIBLE.\n\nDifferent from `POST /warmup/{mailbox_id}/disable`, which pauses warmup\nand keeps the account: this deletes it at the provider and clears every\nwarmup field on the mailbox, so re-enrolling starts the reputation build\nfrom zero. Disable is what you want for a pause.\n\nBest-effort at the provider: if the provider call fails the local fields\nare still cleared, so a success here means graph8 no longer considers the\nmailbox warmed - confirm with `GET /warmup/{mailbox_id}/analytics`.","operationId":"delete_warmup_warmup__mailbox_id__delete","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Mailbox id (mailboxes.id)","title":"Mailbox Id"},"description":"Mailbox id (mailboxes.id)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/mailboxes/personas":{"get":{"tags":["Mailboxes"],"summary":"List Sender Personas","description":"The org's sender personas, with how many mailboxes each one holds.\n\nOrg admins and owners only, and a personal API key: a persona carries a\nreal person's identity details.","operationId":"list_sender_personas_mailboxes_personas_get","parameters":[{"name":"include_archived","in":"query","required":false,"schema":{"type":"boolean","description":"Include archived personas","default":false,"title":"Include Archived"},"description":"Include archived personas"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"post":{"tags":["Mailboxes"],"summary":"Create Sender Persona","description":"Create a sender persona - an identity mailboxes can be bought under.\n\nGive `first_name`, `last_name` and `email`, or a `team_member_id` to take\nthem from. The identity is registrant data at the registrar for every\ndomain bought under it, so use a real person who has agreed to it.\n\n409 if the email is already a persona. Org admins and owners only, and a\npersonal API key.","operationId":"create_sender_persona_mailboxes_personas_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SenderPersonaWriteRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/mailboxes/personas/{persona_id}":{"get":{"tags":["Mailboxes"],"summary":"Get Sender Persona","description":"One sender persona in full, archived or not. Org admins and owners only.","operationId":"get_sender_persona_mailboxes_personas__persona_id__get","parameters":[{"name":"persona_id","in":"path","required":true,"schema":{"type":"integer","exclusiveMinimum":0,"description":"Sender persona id - from GET /mailboxes/personas","title":"Persona Id"},"description":"Sender persona id - from GET /mailboxes/personas"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Mailboxes"],"summary":"Update Sender Persona","description":"Change a sender persona. Send only the fields that change.\n\n`first_name`, `last_name` and `email` cannot be set to null. Domains\nalready registered keep the registrant details they were bought with.\nOrg admins and owners only, and a personal API key.","operationId":"update_sender_persona_mailboxes_personas__persona_id__patch","parameters":[{"name":"persona_id","in":"path","required":true,"schema":{"type":"integer","exclusiveMinimum":0,"description":"Sender persona id - from GET /mailboxes/personas","title":"Persona Id"},"description":"Sender persona id - from GET /mailboxes/personas"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SenderPersonaWriteRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Mailboxes"],"summary":"Archive Persona","description":"Archive a sender persona. It stops being usable for new purchases.\n\nARCHIVES rather than erases: mailboxes already bought under this identity\nkeep working, and the persona stays readable so their provenance is not\nlost. 409 if an active buying plan still depends on it - cancel or finish\nthe plan first.\n\nOrg admins and owners only, and a personal API key: a persona carries a\nreal person's identity details.","operationId":"archive_persona_mailboxes_personas__persona_id__delete","parameters":[{"name":"persona_id","in":"path","required":true,"schema":{"type":"integer","exclusiveMinimum":0,"description":"Sender persona id - from GET /mailboxes/personas","title":"Persona Id"},"description":"Sender persona id - from GET /mailboxes/personas"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/mailboxes/personas/{persona_id}/photo":{"post":{"tags":["Mailboxes"],"summary":"Upload Persona Photo","description":"Set the photo this sender persona uses. Multipart upload.\n\nREPLACES the current photo. The image is stored by graph8 and referenced\nfrom the returned `photo_url`; 503 means photo storage was unavailable and\nthe persona is unchanged, so it is safe to retry.\n\nOrg admins and owners only, and a personal API key.","operationId":"upload_persona_photo_mailboxes_personas__persona_id__photo_post","parameters":[{"name":"persona_id","in":"path","required":true,"schema":{"type":"integer","exclusiveMinimum":0,"description":"Sender persona id - from GET /mailboxes/personas","title":"Persona Id"},"description":"Sender persona id - from GET /mailboxes/personas"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_persona_photo_mailboxes_personas__persona_id__photo_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/mailboxes/my":{"get":{"tags":["Mailboxes"],"summary":"List My Mailboxes","description":"Mailboxes created by the principal behind this key.\n\nHard-scoped server-side to the caller - it does not trust a client-supplied\nowner filter, which is what separates it from the generic mailbox list.","operationId":"list_my_mailboxes_mailboxes_my_get","parameters":[{"name":"include_archived","in":"query","required":false,"schema":{"type":"boolean","description":"Include archived mailboxes.","default":false,"title":"Include Archived"},"description":"Include archived mailboxes."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MyMailboxesResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/mailboxes/fleet-health":{"get":{"tags":["Mailboxes"],"summary":"Get Fleet Health","description":"Deliverability health across every mailbox in the org.\n\nThe roll-up a sending dashboard opens with: how many mailboxes are healthy,\ndegraded or failing, so a rebuilt UI can show the same headline.","operationId":"get_fleet_health_mailboxes_fleet_health_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxFleetHealthResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/mailboxes/{mailbox_id}/health":{"get":{"tags":["Mailboxes"],"summary":"Get Mailbox Health","description":"Deliverability health for one mailbox.","operationId":"get_mailbox_health_mailboxes__mailbox_id__health_get","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Mailbox id.","title":"Mailbox Id"},"description":"Mailbox id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxHealthResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/mailboxes/{mailbox_id}/associated-sequences":{"get":{"tags":["Mailboxes"],"summary":"Get Mailbox Associated Sequences","description":"Every sequence that references this mailbox, at any status.\n\nCheck this before archiving or cancelling a mailbox - the app blocks those\nactions while a sequence is still wired to it, and a rebuilt UI needs the\nsame signal to avoid silently breaking a live send.\n\nExposed as GET rather than the app's POST: it reads and has no body. The\napp's POST is left untouched.","operationId":"get_mailbox_associated_sequences_mailboxes__mailbox_id__associated_sequences_get","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Mailbox id.","title":"Mailbox Id"},"description":"Mailbox id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxAssociatedSequencesResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/mailboxes":{"post":{"tags":["Mailboxes"],"summary":"Create Mailbox","description":"Connect an existing mailbox over IMAP/SMTP.\n\nCredentials are write-only — they are stored encrypted and never returned by\nthis or any other endpoint. Google/Microsoft mailboxes need the browser OAuth\nflow and cannot be connected here.\n\nRoutes to the same ``CreateMailboxHandler`` the in-app \"add mailbox\" screen\nuses, so validation and provider detection behave identically.","operationId":"create_mailbox_mailboxes_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MailboxCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"get":{"tags":["GTM Context"],"summary":"List Mailboxes","description":"List sending mailboxes the authenticated user can access in this org.\n\nBacks the MCP \"pick a mailbox before launching a campaign\" flow.\n\nSources from the canonical ``mailboxes`` table (NOT the\n``ai_inbox_email_cron_jobs`` table the FE picker previously used — that\ntable is the AI-inbox sync state, not the source of truth for which\nmailboxes exist). See ``.claude/agent-context/mailbox-picker-sources-cron-table.md``.\n\nTenant scope: ``mailboxes`` lives in the per-org schema (NOT public —\nthe earlier version of this comment was wrong; see\n``select to_regclass('public.mailboxes')`` returning null vs. the\nper-org row count). Binding the session to ``schema=<org>`` IS the\ntenant boundary; no further org-filter predicate is needed.\n\nPer-row RBAC (``ENFORCE_MAILBOX_PERMISSIONS`` soak flag) is NOT enforced\nhere yet — Phase 3b on issue #7180 — keeping symmetry with the FE\npicker. When that flag flips on, this endpoint will adopt the scope\nfilter alongside the cdp/mailboxes/fetch surface.\n\nHistorical bug (fixed 2026-05-22): the previous implementation appended\n``(t.org_id = :org_id OR m.created_by = :user_id)`` to the WHERE. Both\nhalves silently matched zero rows in prod — ``mailboxes.team_id`` is\nNULL on every row (no team pinning) and ``mailboxes.created_by`` stores\nemail strings, not propelauth UUIDs. Result: the endpoint returned an\nempty list for every caller. Dropping the predicate restores the\ncorrect per-org listing; tenant isolation comes from the schema bind.","operationId":"list_mailboxes_mailboxes_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"include_archived","in":"query","required":false,"schema":{"type":"boolean","description":"Include archived mailboxes","default":false,"title":"Include Archived"},"description":"Include archived mailboxes"},{"name":"connection_status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by connection_status (active|paused|disconnected|expired|...)","title":"Connection Status"},"description":"Filter by connection_status (active|paused|disconnected|expired|...)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/mailboxes/{mailbox_id}":{"get":{"tags":["Mailboxes"],"summary":"Get Mailbox","description":"Get a single mailbox by id. Credentials are never included.","operationId":"get_mailbox_mailboxes__mailbox_id__get","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","description":"Mailbox ID (mailboxes.id)","title":"Mailbox Id"},"description":"Mailbox ID (mailboxes.id)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Mailboxes"],"summary":"Update Mailbox","description":"Update a mailbox. Only supplied fields change; omitted fields are untouched.","operationId":"update_mailbox_mailboxes__mailbox_id__patch","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","description":"Mailbox ID (mailboxes.id)","title":"Mailbox Id"},"description":"Mailbox ID (mailboxes.id)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MailboxUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Mailboxes"],"summary":"Delete Mailbox","description":"Delete a mailbox. Sequences already referencing it stop being able to send from it.","operationId":"delete_mailbox_mailboxes__mailbox_id__delete","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","description":"Mailbox ID (mailboxes.id)","title":"Mailbox Id"},"description":"Mailbox ID (mailboxes.id)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDeleteResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/mailboxes/{mailbox_id}/test-connection":{"post":{"tags":["Mailboxes"],"summary":"Test Mailbox Connection","description":"Verify a mailbox's IMAP/SMTP credentials and refresh its connection status.\n\nSend an empty body to test what is stored. Supply credentials to test\ncandidate values without saving them — useful for validating before a PATCH.","operationId":"test_mailbox_connection_mailboxes__mailbox_id__test_connection_post","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","description":"Mailbox ID (mailboxes.id)","title":"Mailbox Id"},"description":"Mailbox ID (mailboxes.id)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/MailboxTestConnectionRequest"},{"type":"null"}],"title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/placement/tests/estimate":{"post":{"tags":["Mailboxes"],"summary":"Estimate Placement Test Cost","description":"What a placement test WOULD cost, and whether the mailboxes qualify.\n\nCharges nothing. Call this before `POST /placement/tests`, which charges\n20 credits per mailbox - this is the only way to learn the number before\nspending it.","operationId":"estimate_placement_test_cost_placement_tests_estimate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EstimateTestRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeliverabilityPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/placement/tests":{"post":{"tags":["Mailboxes"],"summary":"Create Placement Test","description":"Run an inbox-placement test. THIS CHARGES 20 CREDITS PER MAILBOX.\n\nCharged when the test is CREATED, not when it finishes, so a cancelled or\nfailed test has still cost. Estimate first.\n\nA `frequency` other than `once` creates a recurring schedule that charges\nagain on every run - see `GET /placement/scheduled` and `/pause`.","operationId":"create_placement_test_placement_tests_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateTestRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeliverabilityPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"},"get":{"tags":["Mailboxes"],"summary":"List Placement Tests","description":"Placement tests, newest first.","operationId":"list_placement_tests_placement_tests_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by test status. The wire name is `status`, matching the app; the handler parameter is renamed only because `status` is already imported from FastAPI in this module.","title":"Status"},"description":"Filter by test status. The wire name is `status`, matching the app; the handler parameter is renamed only because `status` is already imported from FastAPI in this module."},{"name":"domain_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Only tests for this domain.","title":"Domain Id"},"description":"Only tests for this domain."},{"name":"mailbox_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Only tests for this mailbox.","title":"Mailbox Id"},"description":"Only tests for this mailbox."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeliverabilityListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/placement/tests/{test_id}":{"get":{"tags":["Mailboxes"],"summary":"Get Placement Test","description":"One test, with a panel per seed provider.\n\nOpen-shaped: the panel set changes as providers are added, and a missing\npanel reads as \"we did not test there\" when the truth may be \"you did not\nland there\".","operationId":"get_placement_test_placement_tests__test_id__get","parameters":[{"name":"test_id","in":"path","required":true,"schema":{"type":"integer","description":"Test id.","title":"Test Id"},"description":"Test id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeliverabilityPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/placement/domains/stats":{"get":{"tags":["Mailboxes"],"summary":"Get Placement Domain Stats","description":"Placement across every sending domain, at a glance.","operationId":"get_placement_domain_stats_placement_domains_stats_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeliverabilityListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/placement/domains/{domain_id}/summary":{"get":{"tags":["Mailboxes"],"summary":"Get Placement Domain Summary","description":"One domain's placement, with its test history paged beneath it.","operationId":"get_placement_domain_summary_placement_domains__domain_id__summary_get","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Domain id.","title":"Domain Id"},"description":"Domain id."},{"name":"history_page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"History Page"}},{"name":"history_limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":20,"title":"History Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeliverabilityPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/placement/scheduled":{"get":{"tags":["Mailboxes"],"summary":"List Scheduled Placement Tests","description":"Every recurring test, and therefore every recurring CHARGE.\n\nRead this before wondering where credits are going: a test created with a\n`frequency` other than `once` charges again on every run until paused.","operationId":"list_scheduled_placement_tests_placement_scheduled_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeliverabilityListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/placement/scheduled/{schedule_id}":{"get":{"tags":["Mailboxes"],"summary":"Get Scheduled Placement Test","description":"One recurring test: its cadence, its mailboxes and its next run.","operationId":"get_scheduled_placement_test_placement_scheduled__schedule_id__get","parameters":[{"name":"schedule_id","in":"path","required":true,"schema":{"type":"string","description":"Schedule id. A STRING, not a number: it is an opaque InboxKit identifier persisted as `inboxkit_schedule_id VARCHAR(100)` and interpolated straight into an InboxKit URL. `test_id`, `domain_id` and `mailbox_id` on this surface really are integers - the app draws the same distinction, and flattening it would 422 every id `GET /placement/scheduled` hands back.","title":"Schedule Id"},"description":"Schedule id. A STRING, not a number: it is an opaque InboxKit identifier persisted as `inboxkit_schedule_id VARCHAR(100)` and interpolated straight into an InboxKit URL. `test_id`, `domain_id` and `mailbox_id` on this surface really are integers - the app draws the same distinction, and flattening it would 422 every id `GET /placement/scheduled` hands back."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeliverabilityPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Mailboxes"],"summary":"Delete Scheduled Placement Test","description":"Remove a recurring test. Tests it has already run are kept.","operationId":"delete_scheduled_placement_test_placement_scheduled__schedule_id__delete","parameters":[{"name":"schedule_id","in":"path","required":true,"schema":{"type":"string","description":"Schedule id. A STRING, not a number: it is an opaque InboxKit identifier persisted as `inboxkit_schedule_id VARCHAR(100)` and interpolated straight into an InboxKit URL. `test_id`, `domain_id` and `mailbox_id` on this surface really are integers - the app draws the same distinction, and flattening it would 422 every id `GET /placement/scheduled` hands back.","title":"Schedule Id"},"description":"Schedule id. A STRING, not a number: it is an opaque InboxKit identifier persisted as `inboxkit_schedule_id VARCHAR(100)` and interpolated straight into an InboxKit URL. `test_id`, `domain_id` and `mailbox_id` on this surface really are integers - the app draws the same distinction, and flattening it would 422 every id `GET /placement/scheduled` hands back."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeliverabilityPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/placement/scheduled/{schedule_id}/pause":{"post":{"tags":["Mailboxes"],"summary":"Pause Scheduled Placement Test","description":"Stop a recurring test charging. Reversible with `/resume`.\n\nPausing does not refund a run already charged; it stops the next one.","operationId":"pause_scheduled_placement_test_placement_scheduled__schedule_id__pause_post","parameters":[{"name":"schedule_id","in":"path","required":true,"schema":{"type":"string","description":"Schedule id. A STRING, not a number: it is an opaque InboxKit identifier persisted as `inboxkit_schedule_id VARCHAR(100)` and interpolated straight into an InboxKit URL. `test_id`, `domain_id` and `mailbox_id` on this surface really are integers - the app draws the same distinction, and flattening it would 422 every id `GET /placement/scheduled` hands back.","title":"Schedule Id"},"description":"Schedule id. A STRING, not a number: it is an opaque InboxKit identifier persisted as `inboxkit_schedule_id VARCHAR(100)` and interpolated straight into an InboxKit URL. `test_id`, `domain_id` and `mailbox_id` on this surface really are integers - the app draws the same distinction, and flattening it would 422 every id `GET /placement/scheduled` hands back."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeliverabilityPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/placement/scheduled/{schedule_id}/resume":{"post":{"tags":["Mailboxes"],"summary":"Resume Scheduled Placement Test","description":"Start a paused recurring test again. IT RESUMES CHARGING.","operationId":"resume_scheduled_placement_test_placement_scheduled__schedule_id__resume_post","parameters":[{"name":"schedule_id","in":"path","required":true,"schema":{"type":"string","description":"Schedule id. A STRING, not a number: it is an opaque InboxKit identifier persisted as `inboxkit_schedule_id VARCHAR(100)` and interpolated straight into an InboxKit URL. `test_id`, `domain_id` and `mailbox_id` on this surface really are integers - the app draws the same distinction, and flattening it would 422 every id `GET /placement/scheduled` hands back.","title":"Schedule Id"},"description":"Schedule id. A STRING, not a number: it is an opaque InboxKit identifier persisted as `inboxkit_schedule_id VARCHAR(100)` and interpolated straight into an InboxKit URL. `test_id`, `domain_id` and `mailbox_id` on this surface really are integers - the app draws the same distinction, and flattening it would 422 every id `GET /placement/scheduled` hands back."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeliverabilityPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/warmup/setup":{"post":{"tags":["Mailboxes"],"summary":"Setup Warmup","description":"Enrol a mailbox with a warmup provider.\n\n`warmup_settings` is passed through untouched: the accepted keys differ\nper provider and change with them, so this contract does not second-guess\nwhat the provider takes.","operationId":"setup_warmup_warmup_setup_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetupWarmupRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeliverabilityPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/warmup/{mailbox_id}/enable":{"post":{"tags":["Mailboxes"],"summary":"Enable Warmup","description":"Start warming this mailbox. It begins SENDING MAIL on its own.","operationId":"enable_warmup_warmup__mailbox_id__enable_post","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","description":"Mailbox id.","title":"Mailbox Id"},"description":"Mailbox id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeliverabilityPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/warmup/{mailbox_id}/disable":{"post":{"tags":["Mailboxes"],"summary":"Disable Warmup","description":"Stop warming this mailbox.\n\nReversible, but reputation is not: a mailbox taken off warmup and left\nidle loses the standing the warmup was building.","operationId":"disable_warmup_warmup__mailbox_id__disable_post","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","description":"Mailbox id.","title":"Mailbox Id"},"description":"Mailbox id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeliverabilityPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/warmup/{mailbox_id}/analytics":{"get":{"tags":["Mailboxes"],"summary":"Get Warmup Analytics","description":"How the warmup is going: volume, landing rate and reputation trend.","operationId":"get_warmup_analytics_warmup__mailbox_id__analytics_get","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","description":"Mailbox id.","title":"Mailbox Id"},"description":"Mailbox id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeliverabilityPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/warmup/{mailbox_id}/settings":{"patch":{"tags":["Mailboxes"],"summary":"Update Warmup Settings","description":"Change how an already-running warmup behaves.\n\nThe body is OPEN and forwarded as-is, matching the app, which types this\nparameter as a bare `Dict[str, Any]` and hands it to the provider. Closing\nit here would reject a setting the provider supports.","operationId":"update_warmup_settings_warmup__mailbox_id__settings_patch","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","description":"Mailbox id.","title":"Mailbox Id"},"description":"Mailbox id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateWarmupSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeliverabilityPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/duplicates":{"get":{"tags":["Duplicates"],"summary":"List Duplicates","description":"List duplicate-suggestion pairs. Proxies the app's own\n``GET /v1/duplicates`` (``duplicates/interfaces/router.py:497``) --\nsee module docstring for why this is a direct function call.","operationId":"list_duplicates_duplicates_get","parameters":[{"name":"entity_type","in":"query","required":true,"schema":{"enum":["contact","company","deal"],"type":"string","title":"Entity Type"}},{"name":"status","in":"query","required":false,"schema":{"type":"string","default":"pending","title":"Status"}},{"name":"owner_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id"}},{"name":"industry","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Industry"}},{"name":"confidence","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Confidence"}},{"name":"lifecycle_stage","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated list of lifecycle stages (e.g. 'lead')","title":"Lifecycle Stage"},"description":"Comma-separated list of lifecycle stages (e.g. 'lead')"},{"name":"created_after","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created After"}},{"name":"created_before","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created Before"}},{"name":"last_activity_after","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Last Activity After"}},{"name":"last_activity_before","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Last Activity Before"}},{"name":"discovered_after","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Discovered After"}},{"name":"discovered_before","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Discovered Before"}},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Search"}},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Cursor"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":25,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/duplicates/counts":{"get":{"tags":["Duplicates"],"summary":"Duplicate Counts","description":"Badge count of pending duplicate suggestions. Proxies\n``GET /v1/duplicates/counts`` (``duplicates/interfaces/router.py:556``).","operationId":"duplicate_counts_duplicates_counts_get","parameters":[{"name":"entity_type","in":"query","required":true,"schema":{"enum":["contact","company","deal"],"type":"string","title":"Entity Type"}},{"name":"lifecycle_stage","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Lifecycle Stage"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/duplicates/recent-merges":{"get":{"tags":["Duplicates"],"summary":"List Recent Merges","description":"Recent merges with undo eligibility. Proxies\n``GET /v1/duplicates/recent-merges`` (``duplicates/interfaces/router.py:899``).\nMake undo discoverable: each row's ``can_undo`` flag tells you whether\n``POST /duplicates/undo-merge/{id}`` below will accept it.","operationId":"list_recent_merges_duplicates_recent_merges_get","parameters":[{"name":"entity_type","in":"query","required":false,"schema":{"anyOf":[{"enum":["contact","company","deal"],"type":"string"},{"type":"null"}],"title":"Entity Type"}},{"name":"include_shadow","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Include Shadow"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":25,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict_str__Any___"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/duplicates/{suggestion_id}/reject":{"post":{"tags":["Duplicates"],"summary":"Reject Suggestion","description":"Mark a pair as not-a-duplicate, permanently. Proxies\n``POST /v1/duplicates/{id}/reject`` (``duplicates/interfaces/router.py:585``).","operationId":"reject_suggestion_duplicates__suggestion_id__reject_post","parameters":[{"name":"suggestion_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"cb_duplicate_suggestions.id","title":"Suggestion Id"},"description":"cb_duplicate_suggestions.id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RejectDuplicateRequest","default":{}}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/duplicates/bulk-merge":{"post":{"tags":["Duplicates"],"summary":"Start Bulk Merge","description":"Merge a group: start a bulk merge run over up to 50 suggestion pairs.\nProxies ``POST /v1/duplicates/bulk-merge``\n(``duplicates/interfaces/router.py:617``) -- same blocker checks, same\nper-pair transactions, same ``MergeContactBlockedError``/\n``MergeCompanyBlockedError`` handling. Returns immediately with a\n``run_id``; poll ``GET /duplicates/bulk-merge/{run_id}`` for progress.\nMerge is destructive: an already-applied pair is only reversible via\n``POST /duplicates/undo-merge/{merge_history_id}`` within its 30-day\nwindow, so check the response and the recent-merges feed rather than\nassuming success.\n\nIdempotency: this is a POST, so it already honours the standard\n``Idempotency-Key`` header via the platform-wide\n``IdempotencyMiddleware`` (``developer_api/dependencies\n/idempotency_middleware.py``) -- no per-route wiring needed. Retrying\nthe same key returns the first run's response instead of starting a\nsecond run.","operationId":"start_bulk_merge_duplicates_bulk_merge_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MergeDuplicatesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:delete","x-graph8-lifecycle":"active"}},"/duplicates/bulk-merge/{run_id}":{"get":{"tags":["Duplicates"],"summary":"Get Bulk Merge Status","description":"Poll a bulk-merge run started via ``POST /duplicates/bulk-merge``\n(this router or the app UI -- same in-process run registry, see module\ndocstring). Proxies ``GET /v1/duplicates/bulk-merge/{run_id}``.","operationId":"get_bulk_merge_status_duplicates_bulk_merge__run_id__get","parameters":[{"name":"run_id","in":"path","required":true,"schema":{"type":"string","title":"Run Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/duplicates/undo-merge/{merge_history_id}":{"post":{"tags":["Duplicates"],"summary":"Undo Merge","description":"Undo a merge within its 30-day recoverability window. Proxies\n``POST /v1/duplicates/undo-merge/{id}``\n(``duplicates/interfaces/router.py:1044``). Contact/company merges only --\nthe app's own merge vocabulary excludes deals here too (see\n``shared/merge/entity_registry.py::SUPPORTED_ENTITY_TYPES``), so this\nroute accepts no ``deal_scope`` either, matching the app function's own\nsignature exactly.","operationId":"undo_merge_duplicates_undo_merge__merge_history_id__post","parameters":[{"name":"merge_history_id","in":"path","required":true,"schema":{"type":"string","title":"Merge History Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/notes":{"get":{"tags":["Notes"],"summary":"List Notes","description":"List all notes on a contact.","operationId":"list_notes_contacts__contact_id__notes_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact ID","title":"Contact Id"},"description":"Contact ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_NoteResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"notes:read","x-graph8-lifecycle":"active"},"post":{"tags":["Notes"],"summary":"Create Note","description":"Create a note on a contact.","operationId":"create_note_contacts__contact_id__notes_post","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact ID","title":"Contact Id"},"description":"Contact ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NoteCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NoteResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"notes:write","x-graph8-lifecycle":"active"}},"/companies/{company_id}/notes":{"get":{"tags":["Notes"],"summary":"List Company Notes","description":"List all notes on a company.","operationId":"list_company_notes_companies__company_id__notes_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"Company ID (mashup_companies.id)","title":"Company Id"},"description":"Company ID (mashup_companies.id)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_NoteResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"notes:read","x-graph8-lifecycle":"active"},"post":{"tags":["Notes"],"summary":"Create Company Note","description":"Create a note on a company.","operationId":"create_company_note_companies__company_id__notes_post","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"Company ID (mashup_companies.id)","title":"Company Id"},"description":"Company ID (mashup_companies.id)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NoteCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NoteResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"notes:write","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/notes":{"get":{"tags":["Notes"],"summary":"List Deal Notes","description":"List all notes on a deal.","operationId":"list_deal_notes_deals__deal_id__notes_get","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal ID (UUID)","title":"Deal Id"},"description":"Deal ID (UUID)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_NoteResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"notes:read","x-graph8-lifecycle":"active"},"post":{"tags":["Notes"],"summary":"Create Deal Note","description":"Create a note on a deal.","operationId":"create_deal_note_deals__deal_id__notes_post","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal ID (UUID)","title":"Deal Id"},"description":"Deal ID (UUID)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NoteCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NoteResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"notes:write","x-graph8-lifecycle":"active"}},"/notes/{note_id}":{"patch":{"tags":["Notes"],"summary":"Update Note","description":"Update a note's content. Works on a contact, company or deal note.","operationId":"update_note_notes__note_id__patch","parameters":[{"name":"note_id","in":"path","required":true,"schema":{"type":"string","description":"Note ID","title":"Note Id"},"description":"Note ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NoteUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NoteResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"notes:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Notes"],"summary":"Delete Note","description":"Delete a note. Works on a contact, company or deal note.","operationId":"delete_note_notes__note_id__delete","parameters":[{"name":"note_id","in":"path","required":true,"schema":{"type":"string","description":"Note ID","title":"Note Id"},"description":"Note ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"notes:delete","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/tasks":{"get":{"tags":["Tasks"],"summary":"List Contact Tasks","description":"List all tasks on a contact.","operationId":"list_contact_tasks_contacts__contact_id__tasks_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact ID","title":"Contact Id"},"description":"Contact ID"},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by status (open, completed)","title":"Status"},"description":"Filter by status (open, completed)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_TaskResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"tasks:read","x-graph8-lifecycle":"active"},"post":{"tags":["Tasks"],"summary":"Create Task","description":"Create a task on a contact.","operationId":"create_task_contacts__contact_id__tasks_post","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact ID","title":"Contact Id"},"description":"Contact ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TaskCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TaskResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"tasks:write","x-graph8-lifecycle":"active"}},"/tasks":{"get":{"tags":["Tasks"],"summary":"List All Tasks","description":"List all tasks org-wide with optional filters.\n\nThe backend list is unpaginated; ``limit``/``offset`` bound the response\nhere (same approach as the MCP ``g8_get_tasks`` tool) so an org with many\ntasks can't return an unbounded payload. Ordering is deterministic\n(``due_date`` asc nulls-last, then ``created_at`` desc), so paging is stable.","operationId":"list_all_tasks_tasks_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by status (open, completed)","title":"Status"},"description":"Filter by status (open, completed)"},{"name":"priority","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","maximum":4,"minimum":0},{"type":"null"}],"description":"Filter by priority","title":"Priority"},"description":"Filter by priority"},{"name":"assignee_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by assignee user ID","title":"Assignee Id"},"description":"Filter by assignee user ID"},{"name":"created_by","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by creator (email or user ID)","title":"Created By"},"description":"Filter by creator (email or user ID)"},{"name":"task_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by task type (call, email, meeting, ...)","title":"Task Type"},"description":"Filter by task type (call, email, meeting, ...)"},{"name":"entity_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by linked entity type (contact, company, deal, team_member)","title":"Entity Type"},"description":"Filter by linked entity type (contact, company, deal, team_member)"},{"name":"entity_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by linked entity ID (pair with entity_type)","title":"Entity Id"},"description":"Filter by linked entity ID (pair with entity_type)"},{"name":"source_meeting_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Filter to tasks from a specific meeting","title":"Source Meeting Id"},"description":"Filter to tasks from a specific meeting"},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Search by task title","title":"Search"},"description":"Search by task title"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Max tasks to return (default 100, max 200)","default":100,"title":"Limit"},"description":"Max tasks to return (default 100, max 200)"},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Number of tasks to skip","default":0,"title":"Offset"},"description":"Number of tasks to skip"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_TaskResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"tasks:read","x-graph8-lifecycle":"active"},"post":{"tags":["Tasks"],"summary":"Create Global Task","operationId":"create_global_task_tasks_post","parameters":[{"name":"idempotency-key","in":"header","required":false,"schema":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Idempotency-Key"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TaskCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TaskResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"tasks:write","x-graph8-lifecycle":"active"}},"/tasks/{task_id}":{"get":{"tags":["Tasks"],"summary":"Get Task","operationId":"get_task_tasks__task_id__get","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","title":"Task Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TaskResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"tasks:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Tasks"],"summary":"Update Task","description":"Update a task.","operationId":"update_task_tasks__task_id__patch","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Task ID","title":"Task Id"},"description":"Task ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TaskUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TaskResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"tasks:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Tasks"],"summary":"Delete Task","description":"Delete a task.","operationId":"delete_task_tasks__task_id__delete","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Task ID","title":"Task Id"},"description":"Task ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"tasks:delete","x-graph8-lifecycle":"active"}},"/tasks/{task_id}/assignment":{"put":{"tags":["Tasks"],"summary":"Assign Task Executor","operationId":"assign_task_executor_tasks__task_id__assignment_put","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Task Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TaskAssignmentRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TaskAssignmentResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"tasks:write","x-graph8-lifecycle":"active"}},"/tasks/{task_id}/start":{"post":{"tags":["Tasks"],"summary":"Start Task Execution","operationId":"start_task_execution_tasks__task_id__start_post","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Task Id"}},{"name":"idempotency-key","in":"header","required":true,"schema":{"type":"string","format":"uuid","title":"Idempotency-Key"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TaskStartResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"tasks:run","x-graph8-lifecycle":"active"}},"/tasks/{task_id}/execution":{"get":{"tags":["Tasks"],"summary":"Task Execution History","operationId":"task_execution_history_tasks__task_id__execution_get","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Task Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TaskExecutionHistory_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"tasks:read","x-graph8-lifecycle":"active"}},"/tasks/{task_id}/copies":{"post":{"tags":["Tasks"],"summary":"Create Task Copies","operationId":"create_task_copies_tasks__task_id__copies_post","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Task Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TaskCopyRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"tasks:write","x-graph8-lifecycle":"active"}},"/fields":{"get":{"tags":["Fields"],"summary":"List Contact Fields","description":"List contact fields (base + custom). Optionally include list-specific custom fields.","operationId":"list_contact_fields_fields_get","parameters":[{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"List ID to include list-specific custom fields","title":"List Id"},"description":"List ID to include list-specific custom fields"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_FieldResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"fields:read","x-graph8-lifecycle":"active"},"post":{"tags":["Fields"],"summary":"Create Field","description":"Create a new custom field (column) for contacts or companies.\n\nSet `list_id` to make the field specific to a single list, or omit it to\ncreate a global field available across every list in the org.\n\nOptionally pass an `enrichment` block to provision a companion waterfall\npipeline in the same request. Without this block the column exists but\nhas no enrichment plan, so `POST /enrichment/waterfall/enrich` later\nreturns 422 (`waterfall_config_missing`).","operationId":"create_field_fields_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateFieldRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CreateFieldResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"fields:write","x-graph8-lifecycle":"active"}},"/fields/companies":{"get":{"tags":["Fields"],"summary":"List Company Fields","description":"List company fields (base + custom). Optionally include list-specific custom fields.","operationId":"list_company_fields_fields_companies_get","parameters":[{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"List ID to include list-specific custom fields","title":"List Id"},"description":"List ID to include list-specific custom fields"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_FieldResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"fields:read","x-graph8-lifecycle":"active"}},"/fields/batch":{"post":{"tags":["Fields"],"summary":"Create Fields Batch","description":"Create many custom columns (contacts or companies) in ONE request.\n\nBacked by a single DB transaction with ONE view rebuild for the whole batch\n— the efficient path for setting up a list with dozens of columns at once.\nThe single-column `POST /fields` is unchanged; this is purely additive.\n\nValidation is fail-fast: data_types, duplicate titles, and every `enrichment`\nblock are checked BEFORE any column is created, so a bad request creates\nnothing. Column creation itself is atomic (all columns or none).\n\nPer-column `enrichment` blocks are applied AFTER the columns commit; if a\ncompanion enrichment config fails for one column, that column still exists\nand its `results[]` entry reports `ok=false` with the error — the rest of\nthe batch is unaffected (mirrors the single endpoint's column-then-config\nordering, but per-field instead of failing the whole request).","operationId":"create_fields_batch_fields_batch_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateFieldsBatchRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CreateFieldsBatchResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"fields:write","x-graph8-lifecycle":"active"}},"/fields/{column_id}":{"delete":{"tags":["Fields"],"summary":"Delete Field","description":"Soft-delete a custom field (column).\n\nAlways org-scoped (you can only delete columns in your own org). Pass\n``list_id`` to additionally require that the column belong to a specific\nlist — that's the safer default for list-scoped agents since the org may\nhave many custom columns across different lists.","operationId":"delete_field_fields__column_id__delete","parameters":[{"name":"column_id","in":"path","required":true,"schema":{"type":"integer","description":"Column ID to delete","title":"Column Id"},"description":"Column ID to delete"},{"name":"entity","in":"query","required":false,"schema":{"type":"string","description":"Target entity: 'contacts' or 'companies'","default":"contacts","title":"Entity"},"description":"Target entity: 'contacts' or 'companies'"},{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Optional list scope guard. If provided, the column must belong to this list or the request returns 404. Use this to prevent an agent with narrow intent from accidentally deleting a column on a different list in the same org.","title":"List Id"},"description":"Optional list scope guard. If provided, the column must belong to this list or the request returns 404. Use this to prevent an agent with narrow intent from accidentally deleting a column on a different list in the same org."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeleteFieldResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"fields:delete","x-graph8-lifecycle":"active"}},"/fields/values/batch":{"patch":{"tags":["Fields"],"summary":"Set Field Values Batch","description":"Write custom column values to one OR many rows in a single call.\n\nThe batch counterpart of ``PATCH /fields/{column_id}/values``. Each row\ncarries its own ``record_id`` and a list of ``{column_id, value}`` pairs;\nevery row shares the top-level ``entity``. A single-row update is just a\n``rows`` list of length one.\n\nPartial success: each row is applied inside its own SAVEPOINT, so a bad row\n(missing record, unknown column) is reported ``ok: false`` in ``results[]``\nwhile the remaining rows still commit. Pass ``value=null`` (or omit it) on a\npair to clear that column for the row.\n\nLimits: 1-500 rows per call; a ``record_id`` may appear only once per call\n(fold that record's writes into one row) - duplicates 400.\n\nEfficiency: all referenced ``column_id``s are resolved in one query and all\n``record_id``s are existence-checked in one query, then each row is written\nwith a single multi-column upsert (N+2 statements, not N*M).","operationId":"set_field_values_batch_fields_values_batch_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetFieldValuesBatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SetFieldValuesBatchResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"fields:write","x-graph8-lifecycle":"active"}},"/fields/{column_id}/values":{"patch":{"tags":["Fields"],"summary":"Set Field Value","description":"Write a custom column value to a single contact or company row.\n\nResolves ``column_id`` to the underlying ``column_name_db`` from\n``dynamic_columns``, then performs an ``INSERT ... ON CONFLICT DO UPDATE``\nagainst ``mashup_contact_attrs`` (or ``mashup_company_attrs`` for companies).\n\nPass ``value=null`` (or omit it) to clear the column for that row.\n\nNotes:\n    - The column must exist in ``dynamic_columns`` (not soft-deleted) for\n      this org and the matching entity. Returns 404 otherwise.\n    - The record (contact or company) must exist - the underlying foreign\n      key constraint enforces this; a missing record yields a 404.\n    - Custom column writes do NOT trigger view recreation; only column\n      creation does (see ``CdpMashupContactRepository.create_column``).","operationId":"set_field_value_fields__column_id__values_patch","parameters":[{"name":"column_id","in":"path","required":true,"schema":{"type":"integer","description":"Column ID from g8_list_fields or g8_create_field","title":"Column Id"},"description":"Column ID from g8_list_fields or g8_create_field"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetFieldValueRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SetFieldValueResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"fields:write","x-graph8-lifecycle":"active"},"get":{"tags":["Fields"],"summary":"Get Field Value","description":"Read a single custom column value for one contact or company row.\n\nThe read-side counterpart of ``PATCH /fields/{column_id}/values``. Resolves\n``column_id`` to the underlying ``column_name_db`` from ``dynamic_columns``\n(scoped by ``object_type`` so a contacts column can't be read through the\ncompanies path), then selects that one value from ``mashup_contact_attrs``\n(or ``mashup_company_attrs`` for companies).\n\nReturns ``value: null`` when the column exists but has never been set for\nthat row. Returns 404 when the column or the record does not exist.\n\nBackwards-compat: this is a brand-new route; no existing surface changes.\nCustom column VALUES are also surfaced inline on the contact/company read\nendpoints when ``include_custom_fields=true`` is passed.","operationId":"get_field_value_fields__column_id__values_get","parameters":[{"name":"column_id","in":"path","required":true,"schema":{"type":"integer","description":"Column ID from g8_list_fields or g8_create_field","title":"Column Id"},"description":"Column ID from g8_list_fields or g8_create_field"},{"name":"record_id","in":"query","required":true,"schema":{"type":"integer","description":"Contact ID (entity='contacts') or company ID (entity='companies')","title":"Record Id"},"description":"Contact ID (entity='contacts') or company ID (entity='companies')"},{"name":"entity","in":"query","required":false,"schema":{"type":"string","description":"Target entity: 'contacts' or 'companies'","default":"contacts","title":"Entity"},"description":"Target entity: 'contacts' or 'companies'"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GetFieldValueResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"fields:read","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/views":{"get":{"tags":["Objects"],"summary":"List Object Views","description":"List this credential's private views and shared workspace views. Views never grant record access.","operationId":"list_object_views_objects__object_slug__views_get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_SavedViewResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"},"post":{"tags":["Objects"],"summary":"Create Object View","description":"Save a private or shared view owned by this credential, without impersonating a human.","operationId":"create_object_view_objects__object_slug__views_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ObjectViewCreate"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SavedViewResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/views/default":{"put":{"tags":["Objects"],"summary":"Set Default Object View","description":"Set or clear this credential's default within this object. Human defaults are unaffected.","operationId":"set_default_object_view_objects__object_slug__views_default_put","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ObjectViewDefault"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Union_SavedViewResponse__NoneType__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/views/{view_id}":{"put":{"tags":["Objects"],"summary":"Update Object View","description":"Rename or replace settings on a view owned by this credential.","operationId":"update_object_view_objects__object_slug__views__view_id__put","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"view_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"View Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ObjectViewUpdate"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SavedViewResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Objects"],"summary":"Delete Object View","description":"Delete a view owned by this credential. Does not delete records.","operationId":"delete_object_view_objects__object_slug__views__view_id__delete","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"view_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"View Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NoneType_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"objects:delete","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/views/board/groups":{"post":{"tags":["Objects"],"summary":"Query Object Board Groups","description":"Read status groups and full filtered counts. This POST performs no writes.","operationId":"query_object_board_groups_objects__object_slug__views_board_groups_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ObjectViewState"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_ObjectBoardGroup__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/views/board/records":{"post":{"tags":["Objects"],"summary":"Query Object Board Records","description":"Read a bounded status page with current record revisions. This POST performs no writes.","operationId":"query_object_board_records_objects__object_slug__views_board_records_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ObjectBoardPage"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RecordListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/imports/csv/inspect":{"post":{"tags":["Objects"],"summary":"Inspect Object Csv Import","description":"Read a CSV's headers, five sample rows and row count. Nothing is stored or written. Maximum 2 MB, 5000 rows, 200 columns.","operationId":"inspect_object_csv_import_objects__object_slug__imports_csv_inspect_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ObjectCsvInspect"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectCsvInspection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/imports/csv/drafts":{"get":{"tags":["Objects"],"summary":"List Object Csv Imports","description":"List this credential's CSV imports for the object, newest first. History only: no file contents or cell values.","operationId":"list_object_csv_imports_objects__object_slug__imports_csv_drafts_get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":25,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","maximum":10000,"minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_ObjectImportSummary__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"},"post":{"tags":["Objects"],"summary":"Create Object Csv Import","description":"Upload a CSV once with its column mapping (header to field slug), mode create or upsert, and matching field for upsert.\nThe file is stored with the import for 30 days or until every row is imported. Writes no records.","operationId":"create_object_csv_import_objects__object_slug__imports_csv_drafts_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ObjectImportCreate"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectImportDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/imports/csv/drafts/{draft_id}":{"get":{"tags":["Objects"],"summary":"Get Object Csv Import","description":"Read one of this credential's imports: setup, headers, progress, status and up to five sample rows while the file is stored.","operationId":"get_object_csv_import_objects__object_slug__imports_csv_drafts__draft_id__get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"draft_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Draft Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectImportDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"},"put":{"tags":["Objects"],"summary":"Update Object Csv Import","description":"Change the filename or setup. revision must be the import's current revision. The stored file never changes.","operationId":"update_object_csv_import_objects__object_slug__imports_csv_drafts__draft_id__put","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"draft_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Draft Id"}},{"name":"revision","in":"query","required":true,"schema":{"type":"integer","minimum":1,"title":"Revision"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ObjectImportUpdate"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectImportDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Objects"],"summary":"Delete Object Csv Import","description":"Delete the stored file and setup. Records already imported, their history and import receipts are kept.","operationId":"delete_object_csv_import_objects__object_slug__imports_csv_drafts__draft_id__delete","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"draft_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Draft Id"}},{"name":"revision","in":"query","required":true,"schema":{"type":"integer","minimum":1,"title":"Revision"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/imports/csv/drafts/{draft_id}/preview":{"post":{"tags":["Objects"],"summary":"Preview Object Csv Import","description":"Preview up to 100 rows of the stored file: normalized values, errors, upsert matches and rows already imported.\nWrites no records. Empty cells are omitted; \\N clears a field.","operationId":"preview_object_csv_import_objects__object_slug__imports_csv_drafts__draft_id__preview_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"draft_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Draft Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ImportPage"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectCsvPreview_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/imports/csv/drafts/{draft_id}/commit":{"post":{"tags":["Objects"],"summary":"Commit Object Csv Import","description":"Commit one previewed page (at most 100 rows) in one transaction. Valid rows are imported; rows that do not validate\nare skipped and listed in skipped_rows (download them from .../errors). Send the page's revision, offset, limit,\nschema_fingerprint and every row's row_number, record_id and revision from the preview. created, updated and skipped\ncount this request; resending a committed page replays its receipts as already_imported and counts nothing twice. A\n409 is never fixed by resending the same body: preview the page again.","operationId":"commit_object_csv_import_objects__object_slug__imports_csv_drafts__draft_id__commit_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"draft_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Draft Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ObjectImportCommit"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectCsvReceipt_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/imports/csv/drafts/{draft_id}/errors":{"get":{"tags":["Objects"],"summary":"Download Object Csv Import Errors","description":"Download skipped and rejected rows as CSV. While the file is stored: the original columns plus row_number, column\nand error, ready to fix and re-upload (cells are spreadsheet-safe). Afterwards: row_number, column and code only,\nnever values. Needs the same read grant as an export.","operationId":"download_object_csv_import_errors_objects__object_slug__imports_csv_drafts__draft_id__errors_get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"draft_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Draft Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"CSV of rejected rows","content":{"application/json":{"schema":{}},"text/csv":{"schema":{"type":"string"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/exports":{"post":{"tags":["Objects"],"summary":"Export Object Records","description":"Download every matching native custom record of a view (filters, search, sort, columns, archived scope) as CSV or\ntyped JSON. Explicit objects:read and objects:export scopes and the key's read grant are required and rechecked before\ndelivery. Maximum 256 MB and 120 seconds; no partial files. CSV is spreadsheet-safe. Not a workspace backup.","operationId":"export_object_records_objects__object_slug__exports_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ObjectExportRequest"}}}},"responses":{"200":{"description":"Complete CSV or JSON file, never a paginated JSON API envelope","content":{"text/csv":{"schema":{"type":"string","format":"binary"}},"application/json":{"schema":{"type":"string","format":"binary"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-response-format":"binary","x-graph8-tier":"write","x-graph8-scope":"objects:export","x-graph8-lifecycle":"active"}},"/process-lists":{"post":{"tags":["Process Lists"],"summary":"Create Process List Api","description":"Create a process list: its object, its parent relationship and the marker, atomically. Requires\nobjects:manage and current Admin access, the same gate as ``POST /objects``. Add the list's fields with\n``POST /objects/{slug}/attributes``.","operationId":"create_process_list_api_process_lists_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProcessListCreate"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ProcessListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:manage","x-graph8-lifecycle":"active"},"get":{"tags":["Process Lists"],"summary":"List Process Lists Api","description":"List the process lists this credential may read. Backing objects are not part of ``GET /objects``.","operationId":"list_process_lists_api_process_lists_get","parameters":[{"name":"include_archived","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Include Archived"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ProcessListListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"}},"/process-lists/{slug}":{"get":{"tags":["Process Lists"],"summary":"Get Process List Api","description":"Read one process list, including its parent binding.","operationId":"get_process_list_api_process_lists__slug__get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","title":"Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ProcessListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Process Lists"],"summary":"Update Process List Api","description":"Rename, describe or archive a list. The parent binding is identity, not a label: it is never accepted here.","operationId":"update_process_list_api_process_lists__slug__patch","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","title":"Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProcessListUpdate"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ProcessListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:manage","x-graph8-lifecycle":"active"},"delete":{"tags":["Process Lists"],"summary":"Archive Process List Api","description":"Archive a list without deleting its entries; restore with PATCH ``is_archived=false``.","operationId":"archive_process_list_api_process_lists__slug__delete","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","title":"Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ProcessListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"objects:manage","x-graph8-lifecycle":"active"}},"/process-lists/{slug}/entries":{"post":{"tags":["Process Lists"],"summary":"Create Process List Entry Api","description":"Create one entry and link it to its parent, atomically. Repeated parents are allowed. A retry with the same\n``idempotency_key`` from the same credential within 24 hours returns the original entry (``replayed: true``);\nreusing the key for a different request is a 409. The entry's own id differs from the parent's.","operationId":"create_process_list_entry_api_process_lists__slug__entries_post","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","title":"Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProcessListEntryCreate"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ProcessListEntryResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/reports":{"get":{"tags":["Reports"],"summary":"List Object Reports Api","description":"List the reports this credential may open: its own, and shared ones whose source it can read. ``owner=me``\nnarrows to this credential's. ``can_share`` says whether it may save a shared report.","operationId":"list_object_reports_api_reports_get","parameters":[{"name":"object_slug","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Object Slug"}},{"name":"owner","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^(me|others)$"},{"type":"null"}],"title":"Owner"}},{"name":"visibility","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^(private|org)$"},{"type":"null"}],"title":"Visibility"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"},"post":{"tags":["Reports"],"summary":"Create Object Report Api","description":"Save a report owned by this credential. Private by default; a shared one (``visibility: \"org\"``) needs\n``objects:manage`` and current Admin access. Fields the credential cannot see are unknown to it.","operationId":"create_object_report_api_reports_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ReportCreate"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportDefinitionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/reports/native-fields":{"get":{"tags":["Reports"],"summary":"List Report Native Fields Api","description":"The contact, company and deal fields a report can group by or filter on through a relationship, with the filter\noperators each accepts, and whether this credential may read each kind at all (`readable`). A schema fact: no record\nis read. A kind is `readable` only when the key's own API scopes and record scope allow it.","operationId":"list_report_native_fields_api_reports_native_fields_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportNativeFieldsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"}},"/reports/preview":{"post":{"tags":["Reports"],"summary":"Preview Object Report Api","description":"Run an unsaved report with this credential's own access and a 10 second budget (nothing partial is returned).","operationId":"preview_object_report_api_reports_preview_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ReportPreview"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"}},"/reports/{report_id}":{"get":{"tags":["Reports"],"summary":"Get Object Report Api","description":"One report. A part of it this credential cannot see comes back as ``{\"id\": ..., \"restricted\": true}``.","operationId":"get_object_report_api_reports__report_id__get","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Report Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportDefinitionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Reports"],"summary":"Update Object Report Api","description":"Edit a report this credential owns. ``expected_revision`` guards a concurrent edit (409).","operationId":"update_object_report_api_reports__report_id__patch","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Report Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ReportUpdate"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportDefinitionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Reports"],"summary":"Archive Object Report Api","description":"Delete (archive) a report this credential owns. Does not touch the source's records.","operationId":"archive_object_report_api_reports__report_id__delete","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Report Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NoneType_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"objects:delete","x-graph8-lifecycle":"active"}},"/reports/{report_id}/execute":{"post":{"tags":["Reports"],"summary":"Execute Object Report Api","description":"Run a saved report as this credential, now or as of a past date; with ``drilldown`` open the records behind a\nnumber. A source that was archived is a 409; a config the schema no longer fits is a 422; over 10 s is a 504.","operationId":"execute_object_report_api_reports__report_id__execute_post","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Report Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ReportRun"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ReportRunApiResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"}},"/workspace/backup":{"post":{"tags":["Workspace backup"],"summary":"Create Workspace Backup Api","description":"Start a backup of everything this key can read in the custom-object workspace (a restricted archive). Its\nhistory (who changed what) is included only for a key holding ``objects:audit``.","operationId":"create_workspace_backup_api_workspace_backup_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BackupJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:export","x-graph8-lifecycle":"active"},"get":{"tags":["Workspace backup"],"summary":"List Workspace Backups Api","description":"This key's backups, newest first, and whether backup storage is configured (a backup answers 503 if not).","operationId":"list_workspace_backups_api_workspace_backup_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BackupJobListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:export","x-graph8-lifecycle":"active"}},"/workspace/backup/{backup_id}":{"get":{"tags":["Workspace backup"],"summary":"Get Workspace Backup Api","description":"One of this key's backups (status, scope, size, sha256, per-section counts, expiry).","operationId":"get_workspace_backup_api_workspace_backup__backup_id__get","parameters":[{"name":"backup_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Backup Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BackupJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:export","x-graph8-lifecycle":"active"}},"/workspace/backup/{backup_id}/download":{"get":{"tags":["Workspace backup"],"summary":"Download Workspace Backup Api","description":"A five-minute link to this key's archive (NDJSON). Refused once the key no longer reads everything in it.","operationId":"download_workspace_backup_api_workspace_backup__backup_id__download_get","parameters":[{"name":"backup_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Backup Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BackupDownloadResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:export","x-graph8-lifecycle":"active"}},"/workspace/restore":{"post":{"tags":["Workspace backup"],"summary":"Create Workspace Restore Api","description":"Restore a completed backup of this workspace as this key (its write grants apply): a dry run unless\n``dry_run`` is false.","operationId":"create_workspace_restore_api_workspace_restore_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RestoreCreate"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RestoreJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:restore","x-graph8-lifecycle":"active"},"get":{"tags":["Workspace backup"],"summary":"List Workspace Restores Api","description":"This key's restores, newest first (status and progress, without the receipt: read one restore for that).","operationId":"list_workspace_restores_api_workspace_restore_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"default":10,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RestoreJobListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:restore","x-graph8-lifecycle":"active"}},"/workspace/restore/{restore_id}":{"get":{"tags":["Workspace backup"],"summary":"Get Workspace Restore Api","description":"One restore this key started: status, per-section counts and one page of its receipt (every conflict: section,\nid, field slug, why, fix; never a value).","operationId":"get_workspace_restore_api_workspace_restore__restore_id__get","parameters":[{"name":"restore_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Restore Id"}},{"name":"conflict_offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Conflict Offset"}},{"name":"conflict_limit","in":"query","required":false,"schema":{"type":"integer","maximum":1000,"minimum":1,"default":200,"title":"Conflict Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RestoreJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:restore","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/records/bulk-archive":{"post":{"tags":["Objects"],"summary":"Bulk Archive Object Records","description":"Archive each listed record, each in its own savepoint, in one commit.\n\nSame rules and audit entry as `DELETE /objects/{slug}/records/{id}`. Nothing is destroyed: archived records stay\nreadable by id and `POST .../records/bulk-restore` undoes exactly the `succeeded` ids. Needs `objects:delete` and\nthe credential's own delete grant on the object. A record id from another organisation or another object is\nreported under `failed`, never archived.","operationId":"bulk_archive_object_records_objects__object_slug__records_bulk_archive_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RecordBulkArchiveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RecordBulkArchiveResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:delete","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/records/bulk-restore":{"post":{"tags":["Objects"],"summary":"Bulk Restore Object Records","description":"Restore each listed record: the inverse of `bulk-archive`.\n\nSame rules as the single restore: a snapshot the current attribute rules reject fails on its own row, under\n`failed`, without stopping the others. Needs `objects:write` and the credential's write grant on the object.","operationId":"bulk_restore_object_records_objects__object_slug__records_bulk_restore_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RecordBulkArchiveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RecordBulkArchiveResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/audit":{"get":{"tags":["Objects"],"summary":"Get Object Audit Log","description":"Who did what, when, to this object's records, newest first.\n\nDiscloses actor activity, so it needs the app's separate audit permission as well as `objects:read`. The credential\nsees only what its own grants and field visibility allow: before/after values of hidden fields are removed and an\nupdate of hidden fields only is absent.","operationId":"get_object_audit_log_objects__object_slug__audit_get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"record_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"description":"Limit to one record of this object (404 if not its).","title":"Record Id"},"description":"Limit to one record of this object (404 if not its)."},{"name":"action","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"description":"Only this action, e.g. `create`.","title":"Action"},"description":"Only this action, e.g. `create`."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AuditLogResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/records/{record_id}/relationships/{definition_id}/targets":{"get":{"tags":["Objects"],"summary":"List Relationship Targets","description":"Candidate records for a NEW link from this record: the write-side picker.\n\nNeeds `objects:read` and `objects:write`. Only far-end records the credential may read are offered.","operationId":"list_relationship_targets_objects__object_slug__records__record_id__relationships__definition_id__targets_get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"record_id","in":"path","required":true,"schema":{"type":"string","title":"Record Id"}},{"name":"definition_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Definition Id"}},{"name":"search","in":"query","required":false,"schema":{"type":"string","maxLength":100,"default":"","title":"Search"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","maximum":10000,"minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RelationshipTargetsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/relationships/cells":{"post":{"tags":["Objects"],"summary":"Query Relationship Cells","description":"Relationship columns for a page of rows: up to two linked-record chips and the visible total per cell.\n\nA read (POST only because the row ids travel in the body). Rows and far records the credential may not see\ncontribute neither chips nor counts.","operationId":"query_relationship_cells_objects__object_slug__relationships_cells_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RelationshipGridCellsQuery"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RelationshipGridCellsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/relationships":{"post":{"tags":["Objects"],"summary":"Create Relationship Definition","description":"Define a relationship from this object to another custom object or to contacts, companies or deals.\n\nSchema administration: needs `objects:manage` and Admin access. A refusal's `detail` is `{code, message}`:\n`slug_conflict` / `schema_change_in_progress` (409), `not_found` (404, the target), `source_not_found` (404),\n`unsupported_target` (422).","operationId":"create_relationship_definition_objects__object_slug__relationships_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RelationshipDefinitionCreate"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RelationshipDefinitionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:manage","x-graph8-lifecycle":"active"},"get":{"tags":["Objects"],"summary":"Get Object Relationship Definitions","description":"Definitions involving a custom or native object, narrowed to the credential's native read scopes.","operationId":"get_object_relationship_definitions_objects__object_slug__relationships_get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","maximum":10000,"minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RelationshipDefinitionListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/attributes/{attr_slug}/recalculate":{"post":{"tags":["Objects"],"summary":"Recalculate Computed Field","description":"Queue a recompute of one computed field for every record of the object.\n\nSchema administration (`objects:manage` plus Admin), and the credential needs the object's write grant. Returns\nhow many jobs were queued; poll `computed-status` for progress. Spends no credits.","operationId":"recalculate_computed_field_objects__object_slug__attributes__attr_slug__recalculate_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"attr_slug","in":"path","required":true,"schema":{"type":"string","title":"Attr Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RecalculateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:manage","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/records/computed-state":{"post":{"tags":["Objects"],"summary":"Query Computed State","description":"Which of these records have a computed field being recalculated or in error.\n\nA read (POST only because the page of ids travels in the body). Fields the credential cannot see are not reported.","operationId":"query_computed_state_objects__object_slug__records_computed_state_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ComputedStateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ComputedStateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/attributes/{attr_slug}/computed-status":{"get":{"tags":["Objects"],"summary":"Get Computed Status","description":"Whether this computed field is being recalculated, has failed, and when it last finished.\n\nA field hidden from the credential is a 404, exactly like one that does not exist.","operationId":"get_computed_status_objects__object_slug__attributes__attr_slug__computed_status_get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"attr_slug","in":"path","required":true,"schema":{"type":"string","title":"Attr Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ComputedStatusResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/attributes/{attr_slug}/dependents":{"get":{"tags":["Objects"],"summary":"Get Field Dependents","description":"Every computed field computed from this field, directly or through rollups.\n\nSchema administration only (`objects:manage` plus Admin): a count of hidden dependents tells a member that fields\nthey cannot see read this one. Dependents the credential cannot see are counted, not listed.","operationId":"get_field_dependents_objects__object_slug__attributes__attr_slug__dependents_get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"attr_slug","in":"path","required":true,"schema":{"type":"string","title":"Attr Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DependentsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:manage","x-graph8-lifecycle":"active"}},"/workflow-records/trigger-objects":{"get":{"tags":["Objects"],"summary":"List Workflow Trigger Objects","description":"The custom objects the credential may read, then the process lists it may read, as workflow trigger sources.","operationId":"list_workflow_trigger_objects_workflow_records_trigger_objects_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkflowTriggerObjectsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"}},"/org/settings/custom-object-capabilities":{"get":{"tags":["Objects"],"summary":"Get Custom Object Capabilities","description":"Which custom-object features (records, formulas, relationships, reports, saved views) are on for the organisation.\n\nA feature that is off answers 404 on its own routes. Booleans about the organisation only; no record data.","operationId":"get_custom_object_capabilities_org_settings_custom_object_capabilities_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CustomObjectCapabilitiesResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"}},"/objects":{"post":{"tags":["Objects"],"summary":"Create Object","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nCreate a native custom object. Requires objects:manage and Admin access.","operationId":"create_object_objects_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ObjectCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectDefinitionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:manage","x-graph8-lifecycle":"preview"},"get":{"tags":["Objects"],"summary":"List Objects","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nList accessible registered standard and custom objects; optionally include archived custom definitions.","operationId":"list_objects_objects_get","parameters":[{"name":"include_archived","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Include Archived"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_ObjectDefinitionResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"preview"}},"/objects/{object_slug}":{"patch":{"tags":["Objects"],"summary":"Update Object","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nRename, archive or restore a custom object while retaining its slug and data. Archiving is refused (409\n`formula_dependency`) while a computed field elsewhere reads it, naming every dependent the credential may see.","operationId":"update_object_objects__object_slug__patch","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ObjectUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectDefinitionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:manage","x-graph8-lifecycle":"preview"},"delete":{"tags":["Objects"],"summary":"Archive Object","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nArchive a custom object without deleting data; restore with PATCH is_archived=false. Refused (409\n`formula_dependency`) while a computed field elsewhere reads it, naming every dependent the credential may see.","operationId":"archive_object_objects__object_slug__delete","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectDefinitionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"objects:manage","x-graph8-lifecycle":"preview"},"get":{"tags":["Objects"],"summary":"Get Object","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nFetch one accessible registered standard or custom object type by its slug.","operationId":"get_object_objects__object_slug__get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectDefinitionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"preview"}},"/objects/{object_slug}/attributes":{"post":{"tags":["Objects"],"summary":"Create Attribute","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nCreate a typed CRM field. Requires objects:manage and current Admin access. A computed field is checked against\nthe schema the credential may see (an admin key included): a field it cannot see or an object it cannot read is\n`unknown_field` / `unknown_relationship` (422), exactly as validate answers.","operationId":"create_attribute_objects__object_slug__attributes_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AttributeCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AttributeDefinitionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:manage","x-graph8-lifecycle":"preview"},"get":{"tags":["Objects"],"summary":"List Object Attributes","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nList active fields. Archived-field discovery currently applies to custom objects.","operationId":"list_object_attributes_objects__object_slug__attributes_get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"include_archived","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Include Archived"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_AttributeDefinitionResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"preview"}},"/objects/{object_slug}/attributes/{attr_slug}":{"patch":{"tags":["Objects"],"summary":"Update Attribute","description":"Edit or restore a field; omitted values remain unchanged. Type and slug are immutable. A change that would\nbreak a computed field is refused (409 `formula_dependency`) with every dependent the credential may see.","operationId":"update_attribute_objects__object_slug__attributes__attr_slug__patch","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"attr_slug","in":"path","required":true,"schema":{"type":"string","title":"Attr Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AttributeUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AttributeDefinitionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:manage","x-graph8-lifecycle":"active"},"delete":{"tags":["Objects"],"summary":"Archive Attribute","description":"Archive a custom field, retaining its values. Restore with PATCH is_archived=false. Refused (409\n`formula_dependency`) while a computed field reads it, with every dependent the credential may see.","operationId":"archive_attribute_objects__object_slug__attributes__attr_slug__delete","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"attr_slug","in":"path","required":true,"schema":{"type":"string","title":"Attr Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AttributeDefinitionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"objects:manage","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/attributes/formula/validate":{"post":{"tags":["Objects"],"summary":"Validate Formula","description":"Dry-run type-check and cycle-check of a typed formula expression, optionally evaluated on one record.\nNothing is stored. Read-only (`objects:read`) despite the POST verb: the expression travels in the body. The\ncheck uses YOUR view of the schema: a field you cannot see or an object you cannot read is unknown, and a preview\nthat names one is `valid: false` with `unknown_field` (200), exactly like a name that does not exist. An admin key\nis held to the same object grants: API keys never bypass them.","operationId":"validate_formula_objects__object_slug__attributes_formula_validate_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormulaValidateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormulaValidateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/records":{"get":{"tags":["Objects"],"summary":"List Object Records","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nList an object's records, newest last, with their active values.\n\nArchived records are excluded. Supports page-number and opaque cursor\npagination; when `cursor` is supplied it wins. Deals use canonical UUIDs,\ncurrent ownership scope, typed values and independently permitted references.","operationId":"list_object_records_objects__object_slug__records_get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (ignored when `cursor` is supplied)","default":1,"title":"Page"},"description":"Page number (ignored when `cursor` is supplied)"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page","default":50,"title":"Limit"},"description":"Items per page"},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Opaque pagination cursor from a prior response's `next_cursor`. When supplied it takes precedence over `page`.","title":"Cursor"},"description":"Opaque pagination cursor from a prior response's `next_cursor`. When supplied it takes precedence over `page`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_ObjectRecordResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"preview"},"post":{"tags":["Objects"],"summary":"Create Object Record","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nCreate a record.\n\nEvery field is validated against the object's attribute definitions. Unknown\nfields are rejected with 422 — they are not dropped — and the response lists\nevery problem at once so a client fixes them in one round trip. A collision on\na unique attribute returns 409.","operationId":"create_object_record_objects__object_slug__records_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RecordWriteRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectRecordResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"preview"}},"/objects/{object_slug}/records/upsert":{"post":{"tags":["Objects"],"summary":"Upsert Object Record","description":"Create (201) or update (200) by a unique key, preserving omitted fields.\n\nA revision requires an existing matching record; a stale or absent match\nreturns 409. Validation, matching, and mutation share one transaction.","operationId":"upsert_object_record_objects__object_slug__records_upsert_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RecordUpsertRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectRecordResponse_"}}}},"201":{"description":"Record created","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectRecordResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/records/bulk":{"patch":{"tags":["Objects"],"summary":"Bulk Update Object Records","description":"Apply the same values to every record in an explicit or filtered scope.\n\nRegistered before ``/{object_slug}/records/{record_id}``: routes match by\npath shape, so \"bulk\" would otherwise bind to ``{record_id}``. Needs\nobjects:read as well as objects:write (a filtered scope echoes the ids that\nmatch caller-chosen predicates). Delegates to the Studio function, so the\nserver-side filter resolution, the 500-row cursor, the per-row savepoints\nand the per-org ``records_core`` switch (404 while off) are identical.","operationId":"bulk_update_object_records_objects__object_slug__records_bulk_patch","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RecordBulkUpdate"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RecordBulkUpdateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/records/merge":{"post":{"tags":["Objects"],"summary":"Merge Object Records","description":"Eligible merge: resolve fields, archive the secondary (its values closed\nfirst), repoint links and associations onto the primary, write the primary.\nNeeds objects:write AND objects:delete — both scope dependencies are real\nparameters so each carries its own ``required_api_key_scope`` marker.\nDelegates to the Studio function (same blockers, field resolution, cascade,\nfar-end access rule and ``records_core`` switch).","operationId":"merge_object_records_objects__object_slug__records_merge_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RecordMergeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RecordMergeResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/records/{record_id}":{"get":{"tags":["Objects"],"summary":"Get Object Record","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nFetch one record with its currently active values.\n\nContacts and companies retain their canonical graph8 IDs; deals retain their\ncanonical UUIDs. Deal values include active typed fields and permitted\ncompany, primary-contact and contact_ids references. Related-record access is checked\nindependently of deal access. Generic deal mutations are not yet supported.","operationId":"get_object_record_objects__object_slug__records__record_id__get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"record_id","in":"path","required":true,"schema":{"type":"string","title":"Record Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectRecordResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"preview"},"patch":{"tags":["Objects"],"summary":"Update Object Record","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nUpdate a record's values. Only the supplied attributes are touched.\n\nA partial update, so required attributes you do not send are left alone rather\nthan reported missing. Sending an explicit `null` CLEARS that attribute.\nValues are versioned rather than overwritten, so the previous value stays\nreadable through the history endpoint.","operationId":"update_object_record_objects__object_slug__records__record_id__patch","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"record_id","in":"path","required":true,"schema":{"type":"string","title":"Record Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RecordUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectRecordResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"preview"},"delete":{"tags":["Objects"],"summary":"Archive Object Record","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nArchive a record.\n\nThe record is hidden from listings but stays readable by id, and its history\nand associations are preserved. Nothing is destroyed.","operationId":"archive_object_record_objects__object_slug__records__record_id__delete","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"record_id","in":"path","required":true,"schema":{"type":"string","title":"Record Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectRecordResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"objects:delete","x-graph8-lifecycle":"preview"}},"/objects/{object_slug}/records/{record_id}/restore":{"post":{"tags":["Objects"],"summary":"Restore Object Record","description":"Restore the archived values under current constraints, preserving identity and history.\n\nUnique-value conflicts return 409. Invalid schema/references or an ambiguous\nlegacy archive snapshot return 422. Retrying an already restored record is a\nread with no additional revision or history generation.","operationId":"restore_object_record_objects__object_slug__records__record_id__restore_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"record_id","in":"path","required":true,"schema":{"type":"string","title":"Record Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectRecordResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/records/{record_id}/history":{"get":{"tags":["Objects"],"summary":"Get Object Record History","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nA record's value timeline, newest first.\n\nEach entry is one generation of one attribute. An entry whose `active_until`\nis null is the value currently in force.","operationId":"get_object_record_history_objects__object_slug__records__record_id__history_get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"record_id","in":"path","required":true,"schema":{"type":"string","title":"Record Id"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"description":"Maximum generations to return","default":100,"title":"Limit"},"description":"Maximum generations to return"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RecordHistoryResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"preview"}},"/objects/{object_slug}/records/{record_id}/changes":{"get":{"tags":["Objects"],"summary":"Get Object Record Changes","description":"Read recorded mutation authorship and before/after changes with stable cursor pagination.\n\nCustom records include clear and lifecycle actions. Canonical contacts and companies use\ntheir existing IDs and audit facts, bounded by current record access and\nfield privacy; archived records are unavailable through this reader.\nOlder writes without recorded mutation facts are not reconstructed here.\nAn unavailable audit store returns 503, never an empty success response.","operationId":"get_object_record_changes_objects__object_slug__records__record_id__changes_get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"record_id","in":"path","required":true,"schema":{"type":"string","title":"Record Id"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":100,"title":"Limit"}},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":512},{"type":"null"}],"title":"Cursor"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RecordMutationsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/records/{record_id}/relationships":{"get":{"tags":["Objects"],"summary":"Get Object Relationships","description":"Read authorized links of a custom or native record, both endpoints filtered\nbefore pagination. Needs objects:read plus the native kinds' explicit read\nscopes; an absent and an inaccessible record share a neutral 404.","operationId":"get_object_relationships_objects__object_slug__records__record_id__relationships_get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"record_id","in":"path","required":true,"schema":{"type":"string","title":"Record Id"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","maximum":10000,"minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RecordRelationshipsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"objects:read","x-graph8-lifecycle":"active"},"post":{"tags":["Objects"],"summary":"Create Object Relationship","description":"Link from a custom or canonical native record. The request's expected revisions are\nrelative to the route's record; the response is always in the definition's canonical\ndirection (source = the custom record, target = the native or custom target).","operationId":"create_object_relationship_objects__object_slug__records__record_id__relationships_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"record_id","in":"path","required":true,"schema":{"type":"string","title":"Record Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RelationshipCreate"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RelationshipResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/objects/{object_slug}/records/{record_id}/relationships/{relationship_id}":{"delete":{"tags":["Objects"],"summary":"Delete Object Relationship","description":"Unlink only the edge; both records stay. All three revisions are required.","operationId":"delete_object_relationship_objects__object_slug__records__record_id__relationships__relationship_id__delete","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"record_id","in":"path","required":true,"schema":{"type":"string","title":"Record Id"}},{"name":"relationship_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Relationship Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RelationshipCreate"}}},"description":"Send application/json with definition_id, target_record_id and all three expected revision fields; a missing body or revision field is 422 and nothing is unlinked."},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RelationshipResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"objects:write","x-graph8-lifecycle":"active"}},"/apps":{"get":{"tags":["Apps"],"summary":"List Apps","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nList the apps your organization owns, newest first.","operationId":"list_apps_apps_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_AppResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"preview"},"post":{"tags":["Apps"],"summary":"Create App","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nCreate an app. It starts in `draft` and serves no traffic until published.\n\nThe slug is unique within your organization, not globally — two builders may\nboth ship a `crm`. A collision returns 409 naming `slug`.","operationId":"create_app_apps_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateAppRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"preview"}},"/apps/{app_id}":{"get":{"tags":["Apps"],"summary":"Get App","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nFetch one of your apps by id.","operationId":"get_app_apps__app_id__get","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"preview"}},"/apps/{app_id}/source":{"put":{"tags":["Apps"],"summary":"Set App Source","description":"Bind this app to the repository a build should fetch (J1).\n\nIdempotent, and a REPLACE rather than a merge: every field is written, so\nrebinding from one provider to another cannot leave the previous provider's\ncredential pointer behind. A build fetching a new repo with a stale\ncredential is the failure this shape exists to prevent.\n\nThere is no GET here on purpose. Source is 1:1 with the app and comes back on\n`GET /apps/{app_id}` through `AppResponse`, so a separate read would be a\nsecond thing to keep in step for no new information.\n\n`credential_ref` is a POINTER to a secret, never a secret. The DTO says so and\nthe column comment says so, because a token written here would also live in\nevery backup of the control plane and in this route's own response.","operationId":"set_app_source_apps__app_id__source_put","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AppSourceRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Apps"],"summary":"Clear App Source","description":"Unbind this app's source.\n\nIdempotent: unbinding an app that has no source is a 200 describing an app\nwith no source, not a 404. The caller asked for a state, and that state\nalready holds.\n\nClearing the binding does NOT touch deployments already built from it. A\ndeployment records what was built; rewriting history to match a since-removed\nbinding would make the audit trail lie about what is running.","operationId":"clear_app_source_apps__app_id__source_delete","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"apps:delete","x-graph8-lifecycle":"active"}},"/apps/{app_id}/secrets":{"get":{"tags":["Apps"],"summary":"List App Secrets","description":"Which secrets this app declares, and where they live (M9 item J7).\n\nPOINTERS ONLY. There is no value in the response and no column that could\nhold one: the platform stores which secrets an app declares so a build can be\nrendered, without ever holding what the build will read.\n\nA hosted app needs config -- its own API keys, a database URL, the graph8\ncredential it calls back with -- and there was no route, DTO or operation id\nfor any of it anywhere in the contract.","operationId":"list_app_secrets_apps__app_id__secrets_get","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_AppSecretResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"active"}},"/apps/{app_id}/secrets/{secret_key}":{"put":{"tags":["Apps"],"summary":"Put App Secret","description":"Declare a secret, or rotate where an existing one lives.\n\nUPSERT, not create. Re-declaring a key is a rotation rather than a 409: the\nbuilder is saying the value moved, and refusing would make the common case an\nerror and push them towards delete-then-create, which loses `created_at` and\nbriefly leaves the app declaring nothing.\n\n`provider_ref` is a POINTER. The DTO refuses the obvious credential shapes,\nwhich is a guardrail against the honest mistake rather than a security\ncontrol: nothing can reliably tell a path from a secret, but someone pasting a\nvalue because the field sits next to the key is the likely error, and this\nturns a silent unrecoverable leak into a 422 they read.","operationId":"put_app_secret_apps__app_id__secrets__secret_key__put","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"secret_key","in":"path","required":true,"schema":{"type":"string","title":"Secret Key"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PutAppSecretRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppSecretResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Apps"],"summary":"Delete App Secret","description":"Stop declaring a secret.\n\nRemoves the DECLARATION, not the value: the value lives in the secret manager\nand this surface never had it to delete. A builder revoking a credential has\nto do it there as well, which the description says so nobody assumes this call\nwas enough.\n\n404 when the app declares no such key, so a typo is not reported as a\nsuccessful removal of something else.","operationId":"delete_app_secret_apps__app_id__secrets__secret_key__delete","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"secret_key","in":"path","required":true,"schema":{"type":"string","title":"Secret Key"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"apps:delete","x-graph8-lifecycle":"active"}},"/apps/{app_id}/runtime":{"get":{"tags":["Apps"],"summary":"Get App Runtime","description":"Can this app be built and run yet, and if not, what is missing (M9 J9).\n\nANSWERS FROM THE CONTROL PLANE, AND SAYS SO. It reports what graph8 has\nrecorded: a bound source, an assigned hostname, declared secrets, the last\ndeployment's state. The serving half -- namespace provisioner, registry\ncredentials, and the deployed-image rollout -- now EXISTS as control-plane code\n(#22301), so this no longer blocks on it unconditionally. What it still checks\nis whether that code is CONFIGURED in this environment (`_unset_serving_runtime_vars`):\nreporting `ready: true` with the templates or registry credentials unset would\nbe the most expensive kind of wrong, because a builder would push and wait for\nsomething nothing can serve.\n\n`blockers` is the field that matters. An agent driving a build needs to know\nWHY it cannot proceed; a bare `ready: false` sends it guessing, and guessing\nagainst a deploy pipeline is how you get retry loops.\n\nDeliberately cheap: three reads the caller could make themselves across\n`GET /apps/{id}`, `/secrets` and `/deployments`. It exists so the answer is\ncomputed in one place, because \"am I ready\" is a judgement about which\nprerequisites matter, and three clients would each get it slightly wrong.","operationId":"get_app_runtime_apps__app_id__runtime_get","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppRuntimeResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"apps:run","x-graph8-lifecycle":"active"}},"/apps/{app_id}/status":{"post":{"tags":["Apps"],"summary":"Set App Status","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nMove an app through its lifecycle: `draft` → `published` → `archived`.\n\n`suspended` is the platform's kill switch and is NOT settable here — a builder\nsuspending and un-suspending their own app would defeat it entirely.","operationId":"set_app_status_apps__app_id__status_post","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetAppStatusRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"preview"}},"/apps/{app_id}/installs":{"get":{"tags":["Apps"],"summary":"List App Installs","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nList the client organizations that installed this app, and their consent state.\n\nIncludes revoked and pending installs, not only consented ones — a builder\ndebugging \"why can't my app reach this tenant\" needs to see the revocation,\nand hiding it turns a clear answer into a mystery.","operationId":"list_app_installs_apps__app_id__installs_get","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_InstallationResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"preview"}},"/apps/{app_id}/usage":{"get":{"tags":["Apps"],"summary":"Get App Usage","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nCredits this app consumed in a calendar month, broken down per client org.\n\nThe breakdown keys on the client whose DATA was touched, not on who paid —\nthe builder pays for all of them. A month with no usage returns zeroes rather\nthan 404: \"nothing happened\" is an answer, and a 404 would read as \"no such\napp\".","operationId":"get_app_usage_apps__app_id__usage_get","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"period","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^\\d{4}-\\d{2}$"},{"type":"null"}],"description":"Calendar month `YYYY-MM`. Defaults to the current month.","title":"Period"},"description":"Calendar month `YYYY-MM`. Defaults to the current month."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_UsageSummaryResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"preview"}},"/apps/{app_id}/limit":{"get":{"tags":["Apps"],"summary":"Get App Limit","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nThis app's hard credit cap, or `null` when it is uncapped.\n\n`null` is the real answer, not an empty object: absence of a limit row IS\n\"no cap\", and there is no unlimited sentinel — so an accidental zero can\nnever read as no limit.","operationId":"get_app_limit_apps__app_id__limit_get","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Union_AppLimitResponse__NoneType__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"preview"},"put":{"tags":["Apps"],"summary":"Set App Limit","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nSet this app's hard credit cap for a window.\n\n`set_limit` and `clear_limit` shipped with the repository layer\n(`repositories/usage.py:198,229`), with a Protocol (`contracts.py:957`) and\ntests, and NO route ever called them. So a builder could read their cap and\ncould never set one, and the only way a limit row came into existence was by\nhand.\n\nThat matters more than a missing endpoint usually would: in a builder-pays\nmodel the cap is the entire spend-safety story. Enforcement was complete and\nunreachable.\n\nSame shape as the #16816 bug, where `store_credential` and `revoke_credential`\nshipped without callers so no service token could ever be minted.\n\nSINGULAR `/limit`, not `/limits`. The read half is singular and is frozen\nthat way in `openapi_operation_ids.json` and the published bundle; adding a\nplural verb would put two spellings of one resource in the public contract\nforever.","operationId":"set_app_limit_apps__app_id__limit_put","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetAppLimitRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppLimitResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"preview"},"delete":{"tags":["Apps"],"summary":"Clear App Limit","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nRemove every window's cap for this app, returning it to uncapped.\n\nA DELETE rather than `PUT {\"credit_cap\": 0}`, because absence of a row IS\n\"no cap\" (`contracts.py:655`) and zero is a real cap meaning \"allow nothing\".\nCollapsing the two would make an accidental zero indistinguishable from\nuncapped, in the one place where guessing wrong costs money.\n\nIdempotent: clearing an app that has no cap succeeds.","operationId":"clear_app_limit_apps__app_id__limit_delete","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NoneType_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"apps:delete","x-graph8-lifecycle":"preview"}},"/apps/{app_id}/credentials":{"post":{"tags":["Apps"],"summary":"Create App Credential","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nCreate a service credential for one consented client organization.\n\n**The secret is returned once and never again.** Only its SHA-256 is stored —\n`developer_app_credentials` has no column that could hold a plaintext secret.\nRotate by creating a new credential and revoking the old one.\n\nThe target organization must already have a **consented** installation of\nthis app. A credential for a workspace that never consented would be a\nstanding key into a tenant that never agreed to it, and the M6-1d clamp would\nrefuse every request it minted anyway — failing here says why, instead of\nleaving a credential that silently cannot work.","operationId":"create_app_credential_apps__app_id__credentials_post","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateCredentialRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CreatedCredentialResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"preview"},"get":{"tags":["Apps"],"summary":"List App Credentials","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nList this app's service credentials. Never returns a secret.\n\nIncludes revoked ones: a builder auditing which credentials exist needs to\nsee the one they turned off, and hiding it would make a rotation look like a\ndeletion.","operationId":"list_app_credentials_apps__app_id__credentials_get","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_CredentialResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"preview"}},"/apps/{app_id}/credentials/{client_id}":{"delete":{"tags":["Apps"],"summary":"Revoke App Credential","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nRevoke a service credential. A status flip, never a delete.\n\nDeleting would erase the evidence that the credential ever existed, which is\nprecisely what an incident review needs. Tokens already minted from it are\nNOT retroactively invalid — they expire on their own short TTL — but no new\none can be minted.","operationId":"revoke_app_credential_apps__app_id__credentials__client_id__delete","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"client_id","in":"path","required":true,"schema":{"type":"string","title":"Client Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CredentialResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"apps:delete","x-graph8-lifecycle":"preview"}},"/apps/manifest/validate":{"post":{"tags":["Apps"],"summary":"Validate App Manifest","description":"Validate a `graph8.app.yaml` without applying it. No app id needed.\n\nAnswers 200 whether or not the manifest is valid: the question \"is this\nvalid\" was served correctly even when the answer is no, and a 422 would make\na builder's linter treat a working call as a transport failure. `valid` is\nthe answer; `issues` carries every problem at once, each with a path pointer,\nso a whole file is fixed in one round trip.\n\nRequires an allowlisted builder org but no app, because linting a manifest\nin CI should not require naming an app or holding a credential scoped to one.","operationId":"validate_app_manifest_apps_manifest_validate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ManifestRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ValidateManifestResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"active"}},"/apps/{app_id}/manifest":{"post":{"tags":["Apps"],"summary":"Apply App Manifest","description":"Apply a `graph8.app.yaml` to this app.\n\nPublishes the `objects:` block as a schema version through the same path\n`POST /{app_id}/schema-versions` uses, including the digest idempotency and\nthe failure-isolated tenant fan-out, and stores `frontend:` / `backend:` as\nthe build config a later deploy reads.\n\nRefuses when the manifest's `app.slug` names a DIFFERENT app than the one in\nthe path. Both halves of that mismatch are plausible mistakes -- a copied\nfile, a wrong id in a script -- and either one silently applied would\npublish one app's schema into another app's tenants.\n\nA manifest with no `objects:` publishes nothing. That is not an oversight:\nan empty schema would archive every object the app has ever declared across\nevery consented tenant, so `schema_publish` refuses it, and a build-config\nonly manifest is a legitimate thing to apply.","operationId":"apply_app_manifest_apps__app_id__manifest_post","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ManifestRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ApplyManifestResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"active"}},"/apps/{app_id}/schema-versions":{"post":{"tags":["Apps"],"summary":"Publish App Schema Version","description":"Publish a declared object schema and materialize it across consented tenants.\n\n422 with every validation problem at once, so a builder fixes their whole\nschema in one round trip rather than one error per attempt.\n\nA publish that resolves to an EXISTING version still returns 201 with\n`created: false` -- the resource named by the response exists either way, and\nthe flag is what tells a caller nothing changed.","operationId":"publish_app_schema_version_apps__app_id__schema_versions_post","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PublishSchemaVersionRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PublishSchemaVersionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"active"},"get":{"tags":["Apps"],"summary":"List App Schema Versions","description":"Every schema version for this app, oldest ordinal first.\n\nIncludes drafts and deprecated versions. A builder asking \"what did I ship\nand when\" needs the whole history, and a filtered list would make a\ndeprecated version look deleted.","operationId":"list_app_schema_versions_apps__app_id__schema_versions_get","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_SchemaVersionResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"active"}},"/app-pages":{"post":{"tags":["App Pages"],"summary":"Create App Page","description":"Create a page over one or more data sources.\n\nEvery source is validated against the connector registry BEFORE anything is\npersisted, so a page can never reference a source that cannot be read.\n422 names the offending source rather than failing generically later.","operationId":"create_app_page_app_pages_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateAppPageRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CreatedAppPageResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"active"},"get":{"tags":["App Pages"],"summary":"List App Pages","description":"Your organization's app pages, most recently updated first.","operationId":"list_app_pages_app_pages_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_AppPageResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"active"}},"/app-pages/{page_id}":{"get":{"tags":["App Pages"],"summary":"Get App Page","description":"One page and its bound sources.","operationId":"get_app_page_app_pages__page_id__get","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","title":"Page Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppPageResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"active"},"delete":{"tags":["App Pages"],"summary":"Delete App Page","description":"Delete a page. Its sources and version history go with it.\n\nA real delete, unlike most of the app platform: a page is the builder's own\ngenerated artifact rather than a record of something that happened, so there\nis no audit reason to keep a tombstone.","operationId":"delete_app_page_app_pages__page_id__delete","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","title":"Page Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"apps:delete","x-graph8-lifecycle":"active"}},"/app-pages/{page_id}/generate":{"post":{"tags":["App Pages"],"summary":"Generate App Page","description":"Generate the page from its sources. Asynchronous; poll `/status`.\n\nBilled, and rate-capped per organization per day. The ordering behind this\n(re-authorize every source before spend, consume the cap, mark generating,\nenqueue, refund and mark failed on error) is shared with the internal surface\nrather than reimplemented here.\n\n404 covers both an unknown page and a source that has become unreachable\nsince the page was created. Distinguishing them would let a caller probe\nwhich sources exist.","operationId":"generate_app_page_app_pages__page_id__generate_post","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","title":"Page Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/GenerateAppPageRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GenerateAppPageResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"apps:run","x-graph8-lifecycle":"active"}},"/app-pages/{page_id}/status":{"get":{"tags":["App Pages"],"summary":"Get App Page Status","description":"Is the page built yet?\n\n`has_page` is separate from `status` because a page can be `ready` with no\nstored HTML, and treating that as ready sends a viewer to an empty frame.","operationId":"get_app_page_status_app_pages__page_id__status_get","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","title":"Page Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppPageStatusResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"active"}},"/app-pages/{page_id}/artifact":{"get":{"tags":["App Pages"],"summary":"Get App Page Artifact","description":"The generated HTML and the manifest wiring it to its sources.\n\nThis is the source, for reading or storing. To DISPLAY a page, mint a frame\nsession instead: the HTML is written for a sandboxed origin with an injected\nSDK and is not safe to embed directly in your own document.","operationId":"get_app_page_artifact_app_pages__page_id__artifact_get","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","title":"Page Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppPageArtifactResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"active"}},"/app-pages/{page_id}/chat-edit":{"post":{"tags":["App Pages"],"summary":"Chat Edit App Page","description":"Change the page by describing the change. Billed and rate-capped.\n\nAn edit that would strip every live-data binding is refused: a page whose\ndata wiring is gone renders stale markup that still looks live, which is\nworse than a failed edit. Each accepted edit snapshots a new version.","operationId":"chat_edit_app_page_app_pages__page_id__chat_edit_post","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","title":"Page Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AppPageChatEditRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppPageChatEditResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"active"}},"/app-pages/{page_id}/versions":{"get":{"tags":["App Pages"],"summary":"List App Page Versions","description":"Every stored version of this page, with the instruction that produced it.","operationId":"list_app_page_versions_app_pages__page_id__versions_get","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","title":"Page Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppPageVersionListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"active"}},"/app-pages/{page_id}/versions/{version_num}/restore":{"post":{"tags":["App Pages"],"summary":"Restore App Page Version","description":"Restore an earlier version.\n\nRestoring SNAPSHOTS rather than rewinds: the current page becomes a new\nversion before the old one is applied, so a restore is itself undoable and\nnothing is destroyed.","operationId":"restore_app_page_version_app_pages__page_id__versions__version_num__restore_post","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","title":"Page Id"}},{"name":"version_num","in":"path","required":true,"schema":{"type":"integer","title":"Version Num"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppPageRestoreResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"active"}},"/app-pages/{page_id}/frame-session":{"post":{"tags":["App Pages"],"summary":"Mint App Page Frame Session","description":"Mint a one-shot token for loading this page's sandboxed frame.\n\nThe generated HTML is not safe to embed in your own document: it is written\nfor an isolated, cookieless origin under a `default-src 'none'` policy with\nan injected data SDK. Load the returned `frame_url` in an iframe instead.\n\nSingle use and short lived, by design. A token that could be replayed would\nbe a bearer credential for the page's data, so each load mints a new one.","operationId":"mint_app_page_frame_session_app_pages__page_id__frame_session_post","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","title":"Page Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppPageFrameSessionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"active"}},"/app-pages/{page_id}/actions":{"get":{"tags":["App Pages"],"summary":"List App Page Actions","description":"What this page can do, grouped by the alias each action acts on.\n\nA source that no longer authorizes contributes nothing rather than failing\nthe whole listing: one revoked binding should not make a page's other\nactions undiscoverable.","operationId":"list_app_page_actions_app_pages__page_id__actions_get","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","title":"Page Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppPageActionsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"active"}},"/app-pages/{page_id}/actions/{alias}/{action_name}":{"post":{"tags":["App Pages"],"summary":"Invoke App Page Action","description":"Invoke a declared action on one of this page's bound sources.\n\nThe bound source is RE-AUTHORIZED on every invocation, not just when the\npage was created, so a source revoked since then stops accepting writes\nimmediately rather than at the next regeneration.\n\n`404` covers an unknown page, an alias this page does not bind, and a source\nthat is no longer reachable. They are indistinguishable on purpose: telling\na caller which of the three it was lets a page enumerate what exists.","operationId":"invoke_app_page_action_app_pages__page_id__actions__alias___action_name__post","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","title":"Page Id"}},{"name":"alias","in":"path","required":true,"schema":{"type":"string","title":"Alias"}},{"name":"action_name","in":"path","required":true,"schema":{"type":"string","title":"Action Name"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/InvokeActionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InvokeActionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"active"}},"/agent/sessions/{session_id}/state":{"get":{"tags":["Agents"],"summary":"Get Agent Session State","description":"Everything needed to render one session from cold.\n\nTHREE sources in one answer, and the difference between them matters:\n`messages` are the chat bubbles, `steps` are what the agent actually did\n(tool calls, reasoning summaries) and `work_item_status` is whether it is\nstill going. A session driven by a work item has richer `steps` than\n`messages`, and a plain chat has only `messages` - so a client that renders\nonly one of them will show an empty conversation for half the sessions.\n\n404s on a session the caller cannot see, rather than 403 - existence is not\nleaked by distinguishing the two.","operationId":"get_agent_session_state_agent_sessions__session_id__state_get","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id (UUID).","title":"Session Id"},"description":"Session id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentSessionStatePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/sessions/{session_id}/read":{"put":{"tags":["Agents"],"summary":"Mark Agent Session Read","description":"Mark messages read up to a COUNT, not a flag.\n\nA count higher than the session actually holds is refused with 409 rather\nthan accepted. That looks strict until you consider what accepting it does:\na stale client claiming to have read eleven messages when there are nine\nwould mark the next two read before anyone saw them, and the customer would\nnever be told the agent had replied.\n\nThe app answers 204 with no body; this returns the usual envelope so a\ngenerated SDK has one response shape across the surface.","operationId":"mark_agent_session_read_agent_sessions__session_id__read_put","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id (UUID).","title":"Session Id"},"description":"Session id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SessionReadRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentSessionStatePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/sessions/voice/capability":{"get":{"tags":["Agents"],"summary":"Get Agent Voice Capability","description":"Can this workspace use voice at all, and what does it cost.\n\nThe org-wide answer, with indicative pricing - ask this before building a\nvoice affordance into a UI. The per-session twin\n(`GET /agent/sessions/{session_id}/voice`) answers the same question for one\nconversation and additionally checks the caller owns it.\n\n`available: false` comes with a `reason`, so a client can say WHY rather\nthan hiding the control.","operationId":"get_agent_voice_capability_agent_sessions_voice_capability_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentSessionStatePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/sessions/voice/draft":{"post":{"tags":["Agents"],"summary":"Create Agent Voice Draft","description":"Create an EMPTY session to speak into.\n\nIt creates only the conversation - never a synthetic opening turn from the\nagent. That is deliberate in the app and worth preserving: a fabricated\nfirst message would appear in the transcript as something the agent said\nwhen it had not yet heard anything.\n\n`session_id` is caller-generated, so a client can open its socket and\ncreate the row without a round trip between the two. Sending the same id\ntwice does not create a second session.","operationId":"create_agent_voice_draft_agent_sessions_voice_draft_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VoiceDraftRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentSessionStatePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/sessions/{session_id}/voice":{"get":{"tags":["Agents"],"summary":"Get Agent Session Voice Capability","description":"Can voice be used on THIS session.\n\nDiffers from the workspace answer by also checking the caller owns the\nsession, so it is the one to ask before showing a microphone on a specific\nconversation.","operationId":"get_agent_session_voice_capability_agent_sessions__session_id__voice_get","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id (UUID).","title":"Session Id"},"description":"Session id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentSessionStatePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"},"post":{"tags":["Agents"],"summary":"Start Agent Session Voice","description":"Start speaking with the agent. THIS SPENDS CREDITS AS IT RUNS.\n\nA live metered session: it begins charging when it connects and keeps\ncharging until it is ended or hits `max_credits`. Quote it first.\n\n`max_credits` is a HARD CEILING and is required - there is no default,\nbecause choosing one would mean this contract picking a spending limit on\nthe customer's behalf. `rate_version` must be the one the quote returned.\n\nEnd it with `DELETE /agent/sessions/{session_id}/voice/{voice_id}`. A\nsession left open keeps costing money.","operationId":"start_agent_session_voice_agent_sessions__session_id__voice_post","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id (UUID).","title":"Session Id"},"description":"Session id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VoiceSessionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentSessionStatePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/agent/sessions/{session_id}/voice/quote":{"post":{"tags":["Agents"],"summary":"Quote Agent Session Voice","description":"What a voice session WOULD cost. Charges nothing.\n\nA POST only because the ceilings are a body. It returns a credit figure and\na `rate_version`, and that version is the point: hand it straight to\n`POST /agent/sessions/{session_id}/voice`, which refuses a stale one rather\nthan starting at today's price against yesterday's quote.\n\nTiered as a READ for that reason. It is the only way to learn the price\nbefore committing to it, so a read-only key must be able to call it.","operationId":"quote_agent_session_voice_agent_sessions__session_id__voice_quote_post","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id (UUID).","title":"Session Id"},"description":"Session id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VoiceQuoteRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentSessionStatePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/sessions/{session_id}/voice/{voice_id}":{"delete":{"tags":["Agents"],"summary":"End Agent Session Voice","description":"Stop a live voice session, and stop the meter.\n\nThis is the one that costs money NOT to call. Ending is the only thing that\nstops the charge short of the ceiling, so treat it as part of the start\ncall rather than as cleanup.\n\nThe CONVERSATION survives - this ends the audio session, not the chat. The\ntranscript stays readable through `GET /agent/sessions/{session_id}/state`.","operationId":"end_agent_session_voice_agent_sessions__session_id__voice__voice_id__delete","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id (UUID).","title":"Session Id"},"description":"Session id (UUID)."},{"name":"voice_id","in":"path","required":true,"schema":{"type":"string","description":"Voice session id (UUID) from the start call.","title":"Voice Id"},"description":"Voice session id (UUID) from the start call."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentSessionStatePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"workflows:delete","x-graph8-lifecycle":"active"}},"/agent/chat":{"post":{"tags":["Agents"],"summary":"Post Agent Chat","description":"Say something to the agent and get its answer.\n\n`kind` in the answer says which way the turn went: `chat` is a reply in\n`message`; `work_item` means the agent read the message as a job and\nSTARTED it - `work_item_id` is the work item, and whether its workflow\nactually launched is in `workflow_started`.\n\nEach turn runs a model and is charged. Omit `session_id` to start a new\nsession.","operationId":"post_agent_chat_agent_chat_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentChatRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentConversationPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/agent/sessions/{session_id}/messages":{"post":{"tags":["Agents"],"summary":"Post Agent Session Message","description":"Append a message to an agent session WITHOUT asking for a reply.\n\nNo model runs and nothing is charged: the message is stored in the\nsession's log and shown to anyone watching it. Use `POST /agent/chat` to\nget an answer. A session you cannot see is a 404.","operationId":"post_agent_session_message_agent_sessions__session_id__messages_post","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id (UUID).","title":"Session Id"},"description":"Session id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentSessionMessageRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentConversationPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/oversight":{"get":{"tags":["Agents"],"summary":"Get Agent Oversight","description":"What your agents need from a person, and what they did without asking.\n\nThree groups in one read: `approvals` (work stopped on a decision - each\nrow carries what `POST /agent/approvals/{approval_id}/decide` needs),\n`blockers` (work stopped for another reason, with why) and\n`autonomous_fixes` (changes made on your behalf).\n\nAN EMPTY GROUP SAYS WHY. Read `states`: `ready` means the read worked and\nthere is nothing, `unavailable` means the read failed, `not_recorded`\nmeans nothing is ever recorded there for this org (no skill is dialled to\nact on its own). Every group is capped at `limit` and says so in `bounds`.","operationId":"get_agent_oversight_agent_oversight_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Max rows PER GROUP.","default":50,"title":"Limit"},"description":"Max rows PER GROUP."},{"name":"fix_window_hours","in":"query","required":false,"schema":{"type":"integer","maximum":720,"minimum":1,"description":"How far back autonomous fixes are read.","default":24,"title":"Fix Window Hours"},"description":"How far back autonomous fixes are read."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentConversationPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/sessions/{session_id}/cards/{card_id}/confirm":{"post":{"tags":["Agents"],"summary":"Confirm Agent Session Card","description":"Answer a confirm card the agent posted into a session.\n\nOnboarding runs stop on these (\"is this your company?\", \"are these your\ncompetitors?\") and resume when the answer lands, usually within ten\nseconds. Idempotent for the same `state`.","operationId":"confirm_agent_session_card_agent_sessions__session_id__cards__card_id__confirm_post","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id (UUID).","title":"Session Id"},"description":"Session id (UUID)."},{"name":"card_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"maxLength":200,"description":"The card's id in the session.","title":"Card Id"},"description":"The card's id in the session."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentCardConfirmationRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentConversationPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/copilot/context/load":{"post":{"tags":["Agents"],"summary":"Load Copilot Intent Context","description":"Open a Copilot session already briefed on one buyer-intent keyword.\n\nReturns `session_id`. The session is seeded with the keyword's detail (and\nthe company or contact, if given), so the first question can be about it\nwithout restating it. No model runs here.","operationId":"load_copilot_intent_context_copilot_context_load_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CopilotContextLoadRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentConversationPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/sessions":{"get":{"tags":["Agents"],"summary":"List Agent Sessions","description":"Sessions owned by, or shared with, the principal behind this key.","operationId":"list_agent_sessions_agent_sessions_get","parameters":[{"name":"mode","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter to one session mode.","title":"Mode"},"description":"Filter to one session mode."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Page size (max 200).","default":50,"title":"Limit"},"description":"Page size (max 200)."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Rows to skip.","default":0,"title":"Offset"},"description":"Rows to skip."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentSessionListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"},"post":{"tags":["Agents"],"summary":"Create Agent Session","description":"Open a session, optionally seeded with messages.","operationId":"create_agent_session_agent_sessions_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentSessionCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentSession_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/sessions/{session_id}":{"get":{"tags":["Agents"],"summary":"Get Agent Session","description":"Read one session, including its messages.","operationId":"get_agent_session_agent_sessions__session_id__get","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id.","title":"Session Id"},"description":"Session id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentSession_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Agents"],"summary":"Update Agent Session","description":"Append messages or change the title. Omitted fields are untouched.","operationId":"update_agent_session_agent_sessions__session_id__patch","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id.","title":"Session Id"},"description":"Session id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentSessionUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentSession_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Agents"],"summary":"Delete Agent Session","description":"Delete a session. Owner only - the internal handler enforces that.","operationId":"delete_agent_session_agent_sessions__session_id__delete","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id.","title":"Session Id"},"description":"Session id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"workflows:delete","x-graph8-lifecycle":"active"}},"/agent/sessions/{session_id}/pin":{"post":{"tags":["Agents"],"summary":"Pin Agent Session","description":"Pin or unpin a session. Owner only.","operationId":"pin_agent_session_agent_sessions__session_id__pin_post","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id.","title":"Session Id"},"description":"Session id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentSessionPinRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentSession_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/sessions/{session_id}/rename":{"post":{"tags":["Agents"],"summary":"Rename Agent Session","description":"Rename a session. Owner only.","operationId":"rename_agent_session_agent_sessions__session_id__rename_post","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id.","title":"Session Id"},"description":"Session id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentSessionRenameRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentSession_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/work-items":{"post":{"tags":["Agents"],"summary":"Create Agent Work Item","description":"Start a unit of autonomous work. THE AGENT BEGINS PLANNING IMMEDIATELY.\n\n`agent_id` selects the planner template. A known id gets its own template;\nanything else falls back to `full`, which is why it is an open string\nrather than an enum - an enum would reject the ad-hoc case the planner\nexplicitly supports.\n\n`visibility` defaults to `private`: work started through a key is not\nvisible org-wide unless asked for.\n\n`user_email` defaults to the identity the key was minted under, so the item\nbelongs to a real person rather than to nobody.","operationId":"create_agent_work_item_agent_work_items_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentWorkItemCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentWorkItem_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"},"get":{"tags":["Agents"],"summary":"List Agent Work Items","description":"Work items the caller can see.","operationId":"list_agent_work_items_agent_work_items_get","parameters":[{"name":"statuses","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"string"}},{"type":"null"}],"description":"Status filter, REPEATABLE: `?statuses=running&statuses=queued`. Repeated rather than comma-joined, matching the app - a comma in a status would otherwise split it.","title":"Statuses"},"description":"Status filter, REPEATABLE: `?statuses=running&statuses=queued`. Repeated rather than comma-joined, matching the app - a comma in a status would otherwise split it."},{"name":"agent_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter to one agent.","title":"Agent Id"},"description":"Filter to one agent."},{"name":"include_shared","in":"query","required":false,"schema":{"type":"boolean","description":"Include org-wide shared items as well as the caller's own. True by default, matching the app - set false to see only your own.","default":true,"title":"Include Shared"},"description":"Include org-wide shared items as well as the caller's own. True by default, matching the app - set false to see only your own."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentWorkItemList_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/work-items/{work_item_id}/steer":{"post":{"tags":["Agents"],"summary":"Steer Agent Work Item","description":"Redirect a RUNNING work item at its next safe step boundary.\n\nNot mid-step - that is what makes steering safe at all. The instruction is\npicked up when the agent reaches a boundary, so a steer sent during a long\ntool call lands afterwards rather than corrupting it.\n\nSAFE TO RETRY: `client_turn_id` is a caller-generated idempotency key, and\nthe same id twice comes back `status: \"duplicate\"` rather than queueing a\nsecond instruction into a running agent. Check that field before assuming\na retry did something.","operationId":"steer_agent_work_item_agent_work_items__work_item_id__steer_post","parameters":[{"name":"work_item_id","in":"path","required":true,"schema":{"type":"string","description":"Work item id (UUID).","title":"Work Item Id"},"description":"Work item id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentWorkItemSteerRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/work-items/{work_item_id}/cancel":{"post":{"tags":["Agents"],"summary":"Cancel Agent Work Item","description":"Stop a work item.\n\nStops the LOOP. Anything the agent already did - a sequence launched, a\nrecord written - stays done; cancelling is not an undo.","operationId":"cancel_agent_work_item_agent_work_items__work_item_id__cancel_post","parameters":[{"name":"work_item_id","in":"path","required":true,"schema":{"type":"string","description":"Work item id (UUID).","title":"Work Item Id"},"description":"Work item id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"workflows:delete","x-graph8-lifecycle":"active"}},"/agent/memory":{"get":{"tags":["Agents"],"summary":"Get Agent Memory","description":"What the agent has learned and carries between sessions.\n\nReturned open-shaped: memory is planner state that changes as the platform\ndoes, and on an oversight surface a dropped field reads as an agent knowing\nless than it does.","operationId":"get_agent_memory_agent_memory_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/evidence/pushback":{"get":{"tags":["Agents"],"summary":"Get Agent Pushback Evidence","description":"Where the agent was overruled, and on what.\n\nThe oversight signal worth acting on: it shows which of the agent's\nsuggestions humans rejected, which is how a customer tunes it rather than\nturning it off.","operationId":"get_agent_pushback_evidence_agent_evidence_pushback_get","parameters":[{"name":"window_days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Lookback window in days.","default":30,"title":"Window Days"},"description":"Lookback window in days."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/proactive-opener":{"get":{"tags":["Agents"],"summary":"Get Agent Proactive Opener","description":"What the agent would open a conversation with, unprompted.\n\nA read - it computes a suggestion and starts nothing.","operationId":"get_agent_proactive_opener_agent_proactive_opener_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/work-items/{work_item_id}/pause":{"post":{"tags":["Agents"],"summary":"Pause Agent Work Item","description":"Park a RUNNING work item at its next step. Nothing is undone and the plan is kept.\n\nThe current step finishes first. Only the owner's running work can be paused: a task that is not running any more\nanswers 409. `POST .../resume` continues it from where it stopped; `.../cancel` ends it.","operationId":"pause_agent_work_item_agent_work_items__work_item_id__pause_post","parameters":[{"name":"work_item_id","in":"path","required":true,"schema":{"type":"string","description":"Work item id (UUID).","title":"Work Item Id"},"description":"Work item id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/work-items/{work_item_id}/resume":{"post":{"tags":["Agents"],"summary":"Resume Agent Work Item","description":"Continue a paused work item from where it stopped. 409 when it is not running any more.","operationId":"resume_agent_work_item_agent_work_items__work_item_id__resume_post","parameters":[{"name":"work_item_id","in":"path","required":true,"schema":{"type":"string","description":"Work item id (UUID).","title":"Work Item Id"},"description":"Work item id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/onboarding/entry-point":{"post":{"tags":["Agents"],"summary":"Capture Agent Entry Point","description":"Record which product the customer signed up for. FIRST WRITER WINS.\n\nThe entry point maps 1:1 to a plan template, so it chooses what the agent\nproposes doing first. It is a one-shot ATTRIBUTION, not a settable\npreference: if the org already has one, this call changes nothing and\nreports the existing value.\n\nRead `captured` rather than the status code - a 200 with `captured: false`\nmeans someone else got there first, which is a normal outcome and not an\nerror.","operationId":"capture_agent_entry_point_agent_onboarding_entry_point_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EntryPointCaptureRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OnboardingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/onboarding/attribution":{"post":{"tags":["Agents"],"summary":"Capture Agent Signup Attribution","description":"Record first-touch attribution - UTM tags, ad click ids, landing page.\n\nFIRST WRITER WINS on every key, so this is safe to call once per session\nand safe to retry. Nothing already captured is overwritten.\n\nEvery field is optional, which means an empty body is legal and does\nnothing. The response reports each destination separately\n(`organization_persisted`, `contact_persisted`, ...) because attribution\nlands in more than one place and a partial write is worth knowing about -\n`complete` is the single field that says all of them took.","operationId":"capture_agent_signup_attribution_agent_onboarding_attribution_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignupAttributionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OnboardingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/onboarding/domain-response":{"post":{"tags":["Agents"],"summary":"Submit Agent Domain Response","description":"Answer the agent's \"is this your company domain?\" card.\n\n`domain` is REQUIRED when `confirmed` is false and ignored when it is true.\nThe app enforces that with a 422 of its own, and this mirrors the model\nrather than the check, so a missing domain is refused by the handler with\nits own message rather than by a copy here that could drift.\n\nA corrected domain is persisted immediately, so a late edit is not orphaned\nonce the polling activity has already exited.","operationId":"submit_agent_domain_response_agent_onboarding_domain_response_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DomainConfirmationRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OnboardingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/onboarding/catchup":{"post":{"tags":["Agents"],"summary":"Post Agent Onboarding Catchup","description":"Post ONE batched summary of what finished while the customer was away.\n\nIDEMPOTENT by watermark: a marker on the previous catch-up message is the\nhigh-water mark, so a repeat call posts nothing and comes back\n`posted: false`. Below the app's minimum card count it is also a no-op - a\nsingle completed card does not need a summary.","operationId":"post_agent_onboarding_catchup_agent_onboarding_catchup_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OnboardingCatchupRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OnboardingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/onboarding/discovery":{"get":{"tags":["Agents"],"summary":"Get Agent Discovery","description":"The whole discovery record, plus an honest coverage report.\n\nEVERY field comes back, answered or not - an unanswered one carries\n`status: \"open\"` rather than being absent, so a caller renders a stable\nlist instead of one that grows as the interview proceeds.\n\n`coverage` is the part worth reading: `open_musts` names what still blocks\na launch, `amber_fields` names the working assumptions, and `can_launch` is\nthe single boolean. It is not a percentage, on purpose - a framework with\nsilent gaps is worse than no framework, because the gaps become confident\ncopy three weeks later.","operationId":"get_agent_discovery_agent_onboarding_discovery_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OnboardingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/onboarding/discovery/open":{"post":{"tags":["Agents"],"summary":"Open Agent Discovery","description":"Start the interview: show what the agent already worked out, and ask\nwhere it is wrong.\n\nTakes no body. Degrades gracefully when nothing is readable yet - a\nbrand-new org's site scrape lands minutes after signup, and the app decided\na routing question is a better opener than a spinner.\n\nA VIEW never enrols an org into a kickoff: proposals are only STAGED for an\norg that already has an onboarding room, which is what stops one visit\ngiving an established org a permanent door onto an empty conversation.","operationId":"open_agent_discovery_agent_onboarding_discovery_open_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OnboardingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/onboarding/discovery/ratify":{"post":{"tags":["Agents"],"summary":"Ratify Agent Discovery","description":"Correct what the agent inferred. The customer's word wins over the scrape.\n\n`edits` overrides a value; `confirmed` accepts one as read. Both default to\nempty, so ratifying nothing is a legal no-op rather than a 422 - which is\nwhat makes the call safe to retry.\n\nThe response echoes PROGRESS, not the field list: `fields` comes back empty\nby design because the caller already holds it from `GET /discovery`.","operationId":"ratify_agent_discovery_agent_onboarding_discovery_ratify_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DiscoveryRatifyRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OnboardingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/onboarding/discovery/answer":{"post":{"tags":["Agents"],"summary":"Answer Agent Discovery","description":"Record ONE graded answer.\n\n`grade` is not decoration. A `red` grade stores NO VALUE and burns a rung of\nthe probe ladder - the agent asks again a different way rather than keeping\na guess. Storing an unusable answer as data is how a confident, wrong ICP\ngets built.\n\n`field_key` must be a real framework field; anything else is refused by the\nhandler by name rather than being written as a stray key.","operationId":"answer_agent_discovery_agent_onboarding_discovery_answer_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DiscoveryAnswerRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OnboardingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/onboarding/discovery/turn":{"post":{"tags":["Agents"],"summary":"Take Agent Discovery Turn","description":"One conversational turn of the kickoff. THIS ONE COSTS MONEY.\n\nThe only route on this surface that makes an LLM call, which is why it is\ntiered `billable` and why the app rate-limits it at 20 requests a minute\nper organisation - far above a human conversation, far below anything that\nshows up on a bill. Over that, the app answers 429 with `Retry-After`.\n\nThe model replies AND states what it learned in one forced tool call, so a\nmessage that answers four questions records four fields. Everything it\nclaims is validated before it is written: a key outside the framework is\ndropped, and a `green` with no supporting quote is DOWNGRADED to `amber`\nrather than trusted.\n\nThe turn writes only to the discovery record. It provisions nothing, calls\nno tools, and sends nothing.\n\nThere is no `history` parameter and that is deliberate - see the module\ndocstring.","operationId":"take_agent_discovery_turn_agent_onboarding_discovery_turn_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DiscoveryTurnRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OnboardingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/agent/onboarding/discovery/signals":{"post":{"tags":["Agents"],"summary":"Setup Agent Discovery Signals","description":"Create the global custom column behind each observable trigger.\n\nTakes no body. A signal is defined ONCE for the account and every list\npatches the same column - that is what makes cross-campaign analysis\npossible at all, and why the column is global rather than list-scoped.\n\nTriggers nothing can observe come back as `research` rather than being\nquietly created: they are real and useful, but they belong in the copy\nrather than in the targeting. Promising to watch something nothing watches\nis a program that never fires and a failure nobody can see.","operationId":"setup_agent_discovery_signals_agent_onboarding_discovery_signals_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OnboardingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/onboarding/discovery/project":{"post":{"tags":["Agents"],"summary":"Project Agent Discovery","description":"Turn the interview into real objects: an ICP, a persona, AND A CAMPAIGN.\n\nTakes no body. The campaign is the part that surprises people, so it is\nsaid plainly: this CREATES a campaign and provisions its Work channel. It\ndoes not SEND anything - the campaign sits there for a human to launch -\nwhich is why this is a `write` and not an `external` operation.\n\nIDEMPOTENT: the projection is idempotent by object name, and the build is\nclaim-fenced, so calling twice updates the same ICP and returns the same\ncampaign rather than minting a second one.\n\nPARTIAL SUCCESS IS A REAL OUTCOME. A refused build does not fail the\nprojection, because the ICP and persona are committed by the time the build\nruns and reporting the whole call as failed would send someone to re-run a\nprojection that worked. Read `campaign.ok` in the body; a blocked build\nnames what is still open rather than counting it.","operationId":"project_agent_discovery_agent_onboarding_discovery_project_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OnboardingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/onboarding/discovery/report":{"get":{"tags":["Agents"],"summary":"Get Agent Discovery Report","description":"The closing report: what is filled, which MUSTs are still open, what was\ninferred rather than answered.\n\nDeliberately not a score. The inferred fields are flagged rather than\ncounted, because the useful question at the end of an interview is \"what\ndid we make up\", not \"how far did we get\".","operationId":"get_agent_discovery_report_agent_onboarding_discovery_report_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OnboardingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/onboarding/discovery/campaign-brief":{"get":{"tags":["Agents"],"summary":"Get Agent Discovery Campaign Brief","description":"The campaign brief the record would produce. A PREVIEW - it writes\nnothing.\n\nDeterministic and LLM-free: running it again after two more answers gives\nthe same document plus two facts, not a differently-worded one. That is\nwhat makes it safe to poll while the interview is still going.\n\nIt never fills a gap to look finished. `open_musts` and `assumptions` come\nback alongside the copy, because a brief that reads as complete while four\nmust-answer questions are open is how a silent gap becomes a confident\nwrong campaign.","operationId":"get_agent_discovery_campaign_brief_agent_onboarding_discovery_campaign_brief_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OnboardingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/operators":{"get":{"tags":["Agents"],"summary":"List Agent Operators","description":"Every operator on the bench, with whether it is switched on for you.\n\nThe starting point for this surface: it carries each operator's catalog\nmetadata and its live status - enabled, whether it has ever run, and how\nmany findings it is holding.","operationId":"list_agent_operators_agent_operators_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/operators/summary":{"get":{"tags":["Agents"],"summary":"Get Agent Operators Summary","description":"One digest across the whole bench.\n\nFinding counts here are DISTINCT, not the sum of the per-operator numbers\nfrom `GET /agent/operators`. Shared findings legitimately appear in several\noperators' caches, and adding the cards up counts them more than once - the\napp's own banner did exactly that before this was split out.","operationId":"get_agent_operators_summary_agent_operators_summary_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/operators/operating-model":{"get":{"tags":["Agents"],"summary":"Get Agent Operating Model","description":"The organisation's operating model: which motions it runs, so operators\nknow what \"normal\" looks like here.\n\nRead this before writing it. The write is a whole-document replace.","operationId":"get_agent_operating_model_agent_operators_operating_model_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"},"put":{"tags":["Agents"],"summary":"Put Agent Operating Model","description":"Replace the organisation's operating-model override. PUT SEMANTICS.\n\nThe whole document is replaced: a key absent from `override` is REMOVED,\nnot left alone, and an empty object resets the org to graph8's defaults.\nThat is the app's behaviour and this does not soften it - a partial-update\nspelling here would make the same body mean two different things on two\nsurfaces.\n\nThis is a policy document, not a switch, which is why it is tiered `write`\nwhile `/enabled` is not: it describes the org, and an operator has to be\nturned on separately before anything reads it unattended.","operationId":"put_agent_operating_model_agent_operators_operating_model_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OperatingModelRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/operators/approvals/sources":{"get":{"tags":["Agents"],"summary":"List Agent Operator Approval Sources","description":"Where operator approval tasks come from.\n\nThe vocabulary behind `GET /agent/operators/{operator}/findings` - what\nkinds of thing raise an approval in the first place.","operationId":"list_agent_operator_approval_sources_agent_operators_approvals_sources_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/operators/approvals/{task_id}/operator":{"get":{"tags":["Agents"],"summary":"Get Agent Operator For Approval Task","description":"Which operator raised this approval task.\n\nThe bridge between an approval sitting in someone's queue and the operator\nwhose dial produced it - so a caller can look at the right scorecard before\ndeciding, and can leave feedback against the right operator afterwards.","operationId":"get_agent_operator_for_approval_task_agent_operators_approvals__task_id__operator_get","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Operator approval task id.","title":"Task Id"},"description":"Operator approval task id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/operators/{operator}/status":{"get":{"tags":["Agents"],"summary":"Get Agent Operator Status","description":"Is this operator on, and has it ever run.","operationId":"get_agent_operator_status_agent_operators__operator__status_get","parameters":[{"name":"operator","in":"path","required":true,"schema":{"type":"string","title":"Operator"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/operators/{operator}/health":{"get":{"tags":["Agents"],"summary":"Get Agent Operator Health","description":"This operator's snapshot of the organisation it watches.\n\nOpen-shaped: each operator reports the checks IT runs, and the set grows\nwith the product. A pinned mirror would silently drop a check, and on a\nhealth surface a missing check reads as a passing one.","operationId":"get_agent_operator_health_agent_operators__operator__health_get","parameters":[{"name":"operator","in":"path","required":true,"schema":{"type":"string","title":"Operator"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/operators/{operator}/findings":{"get":{"tags":["Agents"],"summary":"List Agent Operator Findings","description":"What this operator has found and classified, right now.\n\nThe output of unattended work. Findings are what a `DETECT` dial produces;\na `PROPOSE` dial turns some of them into approval tasks a person decides.","operationId":"list_agent_operator_findings_agent_operators__operator__findings_get","parameters":[{"name":"operator","in":"path","required":true,"schema":{"type":"string","title":"Operator"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/operators/{operator}/catalog":{"get":{"tags":["Agents"],"summary":"Get Agent Operator Catalog","description":"Everything this operator is CAPABLE of, whether or not it is enabled.","operationId":"get_agent_operator_catalog_agent_operators__operator__catalog_get","parameters":[{"name":"operator","in":"path","required":true,"schema":{"type":"string","title":"Operator"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/operators/{operator}/actions":{"get":{"tags":["Agents"],"summary":"List Agent Operator Actions","description":"The action descriptors behind this operator's skills.\n\nStatic and org-independent - the same answer for every organisation. It is\nthe definition of what each action does and how reversible it is, which is\nwhat the trust-dial ceiling is computed from.","operationId":"list_agent_operator_actions_agent_operators__operator__actions_get","parameters":[{"name":"operator","in":"path","required":true,"schema":{"type":"string","title":"Operator"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/operators/{operator}/collections":{"get":{"tags":["Agents"],"summary":"List Agent Operator Collections","description":"The knowledge collections this operator reasons from.\n\nSlug, name and a one-line summary only. The BODIES are never returned -\nthey are graph8-managed and locked, and the app does not expose them\neither. This is not a gap in the proxy.","operationId":"list_agent_operator_collections_agent_operators__operator__collections_get","parameters":[{"name":"operator","in":"path","required":true,"schema":{"type":"string","title":"Operator"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/operators/{operator}/scorecard":{"get":{"tags":["Agents"],"summary":"Get Agent Operator Scorecard","description":"Has this operator been right, per skill.\n\nThe number to read before raising a dial. Raising autonomy on a skill with\na bad scorecard is how unattended work becomes unattended damage.","operationId":"get_agent_operator_scorecard_agent_operators__operator__scorecard_get","parameters":[{"name":"operator","in":"path","required":true,"schema":{"type":"string","title":"Operator"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/operators/{operator}/activity":{"get":{"tags":["Agents"],"summary":"List Agent Operator Activity","description":"What this operator actually DID - decided approvals and remediations.\n\nFindings are what it saw; this is what it changed. The audit trail for\nunattended work, and the only place that distinguishes the two.","operationId":"list_agent_operator_activity_agent_operators__operator__activity_get","parameters":[{"name":"operator","in":"path","required":true,"schema":{"type":"string","title":"Operator"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"description":"How many history rows to return. The app's own default is 50 and it declares no ceiling; a bound is added here because an unbounded limit on a public contract is a denial-of-service parameter.","default":50,"title":"Limit"},"description":"How many history rows to return. The app's own default is 50 and it declares no ceiling; a bound is added here because an unbounded limit on a public contract is a denial-of-service parameter."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/operators/{operator}/activity/{task_id}/records":{"get":{"tags":["Agents"],"summary":"List Agent Operator Activity Records","description":"Which records one activity entry touched.\n\nThe row-level detail behind a single thing the operator did: what it\nchanged, not just that it changed something.","operationId":"list_agent_operator_activity_records_agent_operators__operator__activity__task_id__records_get","parameters":[{"name":"operator","in":"path","required":true,"schema":{"type":"string","title":"Operator"}},{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Task id from the activity list.","title":"Task Id"},"description":"Task id from the activity list."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/operators/{operator}/feedback/summary":{"get":{"tags":["Agents"],"summary":"Get Agent Operator Feedback Summary","description":"What people have said about this operator, in aggregate.","operationId":"get_agent_operator_feedback_summary_agent_operators__operator__feedback_summary_get","parameters":[{"name":"operator","in":"path","required":true,"schema":{"type":"string","title":"Operator"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/operators/{operator}/enabled":{"put":{"tags":["Agents"],"summary":"Set Agent Operator Enabled","description":"Switch this operator on or off for the organisation.\n\nTURNING IT ON STARTS UNATTENDED WORK. The operator's monitors begin running\non their own schedule, without anyone asking, and they keep running until\nthis is set back to false. That is why this needs the `run` grant rather\nthan plain write: \"let something act in my org when I am not watching\" is\nnot the same permission as \"edit a record\".\n\nWhat it is allowed to DO once it is on is a separate control - see\n`PUT /agent/operators/{operator}/skills/{skill_key}`. Enabling an operator\nwhose skills are all `OFF` starts nothing.\n\n`enabled` is explicit rather than a toggle, so a retried request is\nidempotent instead of switching it back off.","operationId":"set_agent_operator_enabled_agent_operators__operator__enabled_put","parameters":[{"name":"operator","in":"path","required":true,"schema":{"type":"string","title":"Operator"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OperatorEnabledRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/agent/operators/{operator}/skills":{"get":{"tags":["Agents"],"summary":"List Agent Operator Skills","description":"Each skill this operator has, and how far it may currently go.\n\nThe source of the `skill_key` values the trust-dial write accepts, and the\nplace to read back what a dial actually RESOLVED to after the risk cap was\napplied.","operationId":"list_agent_operator_skills_agent_operators__operator__skills_get","parameters":[{"name":"operator","in":"path","required":true,"schema":{"type":"string","title":"Operator"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/operators/{operator}/skills/{skill_key}":{"put":{"tags":["Agents"],"summary":"Set Agent Operator Trust Dial","description":"Set how far ONE skill may go on its own. THIS GOVERNS UNATTENDED ACTION.\n\nThe trust dial is the control that decides whether a finding stays a\nfinding, becomes an approval a person decides, or is simply DONE. Raising\nit is the single most consequential write on this surface, which is why it\ntakes the `run` grant rather than plain write.\n\nTHE DIAL IS A CEILING REQUEST, NOT A SETTING. The effective autonomy is the\nminimum of this value, the skill's graph8-managed risk cap and the platform\nceiling, so a skill capped at `PROPOSE` stays at `PROPOSE` no matter what\nis sent. Read the response rather than assuming the write took literally.\n\nRead `GET /agent/operators/{operator}/scorecard` first. A dial raised on a\nskill that has been wrong is how unattended work becomes unattended damage.","operationId":"set_agent_operator_trust_dial_agent_operators__operator__skills__skill_key__put","parameters":[{"name":"operator","in":"path","required":true,"schema":{"type":"string","title":"Operator"}},{"name":"skill_key","in":"path","required":true,"schema":{"type":"string","description":"Skill key from `GET /agent/operators/{operator}/skills`.","title":"Skill Key"},"description":"Skill key from `GET /agent/operators/{operator}/skills`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OperatorTrustDialRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/agent/operators/{operator}/recipient":{"get":{"tags":["Agents"],"summary":"Get Agent Operator Recipient","description":"Who currently receives this operator's alerts and owns its approvals.","operationId":"get_agent_operator_recipient_agent_operators__operator__recipient_get","parameters":[{"name":"operator","in":"path","required":true,"schema":{"type":"string","title":"Operator"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"},"put":{"tags":["Agents"],"summary":"Set Agent Operator Recipient","description":"Name the person who owns this operator's approvals.\n\nREPLACES the current recipient - there is one per operator, not a list.\nWorth setting before enabling anything at `PROPOSE`, because an approval\ntask with no owner is an operator that has stopped.","operationId":"set_agent_operator_recipient_agent_operators__operator__recipient_put","parameters":[{"name":"operator","in":"path","required":true,"schema":{"type":"string","title":"Operator"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OperatorRecipientRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/operators/{operator}/approvals/{task_id}/decide":{"post":{"tags":["Agents"],"summary":"Decide Agent Operator Approval","description":"Approve or reject a fix this operator proposed.\n\n`approved` RUNS THE FIX: the operator executes its proposed remediation\nagainst your data, then records the result. `rejected` records the\ndecision and runs nothing. Needs OPERATOR_MANAGE, the same governance gate\nas the trust dials, because this authorises execution.\n\nA task that is not an open approval for this operator is a 404.","operationId":"decide_agent_operator_approval_agent_operators__operator__approvals__task_id__decide_post","parameters":[{"name":"operator","in":"path","required":true,"schema":{"type":"string","title":"Operator"}},{"name":"task_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"maxLength":200,"description":"The approval task id.","title":"Task Id"},"description":"The approval task id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OperatorApprovalDecisionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OperatorPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/agent/approvals/{approval_id}/request-changes":{"post":{"tags":["Agents"],"summary":"Request Agent Approval Changes","description":"Send the agent back to replan, with a reason. THIS REJECTS THE PROPOSAL.\n\nNot a \"hold\" and not a comment: the current proposal is rejected\nATOMICALLY, and the feedback is stored alongside so the next plan is\ninformed rather than identical. If you want the plan to proceed, use\n`POST /agent/approvals/{approval_id}/decide`.\n\nIt FAILS CLOSED on both halves. A deployment that does not have this route\n404s rather than doing something approximate, and a worker that does not\nunderstand the stored feedback still reads the row as a rejection. There is\nno version of \"older software saw this as approval\".\n\nOnce decided, an approval cannot be decided again - the winner is settled\nserver-side, so a second call gets 409 rather than overwriting.","operationId":"request_agent_approval_changes_agent_approvals__approval_id__request_changes_post","parameters":[{"name":"approval_id","in":"path","required":true,"schema":{"type":"string","description":"Approval id (UUID).","title":"Approval Id"},"description":"Approval id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApprovalChangeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentBenchPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/specialists":{"get":{"tags":["Agents"],"summary":"List Agent Specialists","description":"The sub-agents available to be delegated to.\n\nThe bench: who each specialist is, what it is for, and whether it backs the\nChief of Staff. Static and the same for every organisation - it is the\ncatalogue of what the platform can delegate to, not what YOUR org has\nconfigured.\n\nRead it to learn the `agent_id` values `POST /agent/work-items` accepts as\nits planner template. An unknown id there falls back to the general planner\nrather than failing, which is why that field is an open string - this is the\nlist that stops a caller relying on that fallback by accident.","operationId":"list_agent_specialists_agent_specialists_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentBenchListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/mention-search":{"post":{"tags":["Agents"],"summary":"Search Agent Mentions","description":"Resolve an @-mention: what can be referred to in a message to the agent.\n\nSearches people, campaigns, accounts and documents in one call and returns\nthem with a `category`, so a composer can render one picker instead of four.\nA read - it finds things, it changes nothing, and it starts no agent.\n\nA POST only because the filter set is a body. `query` defaults to empty,\nwhich returns the default suggestions rather than nothing, matching the app.\n\nThe app publishes the SAME search at `/v1/copilot/mention-search` from a\nsecond router that lazily imports this one's helpers. One is enough on a\nversioned contract, and this is the one under `/agent`, beside the sessions\nthe mentions are typed into.","operationId":"search_agent_mentions_agent_mention_search_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MentionSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentBenchListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/approvals":{"get":{"tags":["Agent"],"summary":"List Agent Approvals","description":"Pending approvals this key may act on.\n\nAn approval is the loop asking permission before it runs a tool. Each entry\ncarries the `plan_digest` it is bound to and its `expires_at`, so a caller\ncan tell an approval that still describes the plan from one that has drifted.","operationId":"list_agent_approvals_agent_approvals_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_AgentApprovalResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/approvals/history":{"get":{"tags":["Agent"],"summary":"List Agent Approval History","description":"Decided approvals, newest first, same shape as the pending list.\n\nRegistered ABOVE `/approvals/{approval_id}/receipts` so the literal\n`history` segment cannot be captured as an `approval_id`. `GET\n/workflows/dispositions` 404'd in production for exactly that reason until\n2026-08-07; the ordering here is load-bearing, not cosmetic.","operationId":"list_agent_approval_history_agent_approvals_history_get","parameters":[{"name":"decision","in":"query","required":false,"schema":{"anyOf":[{"enum":["approve","reject","edit_and_approve","dismiss"],"type":"string"},{"type":"null"}],"description":"Optional filter on the recorded decision: 'approve', 'reject', 'edit_and_approve' or 'dismiss'. An unrecognised value is rejected with 422 rather than silently ignored.","title":"Decision"},"description":"Optional filter on the recorded decision: 'approve', 'reject', 'edit_and_approve' or 'dismiss'. An unrecognised value is rejected with 422 rather than silently ignored."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_AgentApprovalResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/approvals/{approval_id}/receipts":{"get":{"tags":["Agent"],"summary":"Get Agent Approval Receipts","description":"Signed provenance receipts attributed to one approval.\n\n404 rather than 403 when the approval belongs to another tenant or to\nanother user's private work item: existence never leaks across that\nboundary. Degrades to an empty list on a schema predating the receipt\ncolumns rather than 500ing.","operationId":"get_agent_approval_receipts_agent_approvals__approval_id__receipts_get","parameters":[{"name":"approval_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Approval ID","title":"Approval Id"},"description":"Approval ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentApprovalReceiptsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/approvals/{approval_id}/decide":{"post":{"tags":["Agent"],"summary":"Decide Agent Approval","description":"Approve, reject, or edit-and-approve a pending approval.\n\nUse `{decision, edit_payload}` for the existing decision mode, or exclusively\n`{use_human_authorization: true}` to relay a short-lived decision previously\nreviewed in the browser by the same personal-key owner. The relay accepts\nno caller-authored decision or edit fields. There is no client\nversion to pass: double-decide is settled server-side by `WHERE decided_at\nIS NULL`, so exactly one caller wins and the loser gets 409 rather than\noverwriting the first decision.\n\n`DecideRequest` does not forbid unknown keys, so a misspelled `edit_payload`\nis dropped in silence and an `edit_and_approve` decides as a plain approve.\nThis docstring is the operation description in the published contract, so\ngetting it wrong here ships the wrong shape to every integrator generating a\nclient from the spec, which is exactly how the earlier `expected_version` /\n`edited_payload` error nearly shipped.","operationId":"decide_agent_approval_agent_approvals__approval_id__decide_post","parameters":[{"name":"approval_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Approval ID","title":"Approval Id"},"description":"Approval ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DecideAgentApprovalRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentApprovalResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/agent/runs":{"post":{"tags":["Agent"],"summary":"Create Agent Run","description":"Start a durable agent run.\n\n\"Run\" is the public noun; the stored row is a work item and every internal\nname says so. The same translation `app_pages_router` makes for dashboards,\nand for the same reason: the public contract should read the way a builder\nthinks, not the way the table is named.\n\n`workflow_started: false` is a NORMAL outcome, not an error. The row is\npersisted either way; a false means the Temporal worker did not pick it up\non this attempt and the reason is carried alongside it.","operationId":"create_agent_run_agent_runs_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateAgentRunRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CreatedAgentRunResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"},"get":{"tags":["Agent"],"summary":"List Agent Runs","description":"List runs this key can see: its own, plus org-wide shared ones.\n\nReconciles abandoned rows before reading, so a run whose worker was recycled\nreports `failed` rather than sitting at `running` forever.","operationId":"list_agent_runs_agent_runs_get","parameters":[{"name":"statuses","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"string"}},{"type":"null"}],"description":"Optional repeatable status filter: ?statuses=running&statuses=queued","title":"Statuses"},"description":"Optional repeatable status filter: ?statuses=running&statuses=queued"},{"name":"agent_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent Id"}},{"name":"include_shared","in":"query","required":false,"schema":{"type":"boolean","description":"When true (default), include org-wide shared runs. When false, return only runs this key owns.","default":true,"title":"Include Shared"},"description":"When true (default), include org-wide shared runs. When false, return only runs this key owns."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentRunListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/runs/{run_id}":{"get":{"tags":["Agent"],"summary":"Get Agent Run","description":"Fetch one run.\n\nTHE ONE ROUTE HERE THAT IS NOT PURE DELEGATION, because there is no\n`GET /v1/agent/work-items/{id}` on the JWT surface to call. Without it a\nbuilder can create a run, receive its id, and then have no way to poll it\nexcept by listing everything and filtering client-side.\n\nIts visibility rule is copied from `list_work_items`, NOT from\n`cancel_work_item`: a read may see the caller's own runs plus org-wide\n`visibility='shared'` ones, whereas cancel is owner-only because stopping\nsomeone else's work is destructive. Pinning the read to the stricter rule\nwould hide a shared run that the list route shows, and the two disagreeing\nabout the same row is worse than either answer alone.\n\n404, never 403, on a run the caller may not see: a non-owner must not be\nable to use this route to probe which runs exist in the org. Same reason\n`cancel_work_item` returns 404 for a non-owner.","operationId":"get_agent_run_agent_runs__run_id__get","parameters":[{"name":"run_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Run ID","title":"Run Id"},"description":"Run ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AgentRunResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/agent/runs/{run_id}/cancel":{"post":{"tags":["Agent"],"summary":"Cancel Agent Run","description":"Stop a run and everything it spawned.\n\nOWNER ONLY, and that is stricter than the read routes on purpose: shared\nvisibility lets an org SEE a teammate's run, while stopping it is\ndestructive and not undone by restarting. Children are signalled before the\nroot so a freed parent cannot leave orphans behind it.\n\nIdempotent on an already-terminal run: `cancelled: false` with a reason,\nnot an error, so a double call does not look like a failure.","operationId":"cancel_agent_run_agent_runs__run_id__cancel_post","parameters":[{"name":"run_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Run ID","title":"Run Id"},"description":"Run ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CancelAgentRunResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"workflows:delete","x-graph8-lifecycle":"active"}},"/apps/{app_id}/deployments":{"get":{"tags":["App Deployments"],"summary":"List App Deployments","description":"Every deployment for this app, newest first.","operationId":"list_app_deployments_apps__app_id__deployments_get","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_DeploymentResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"active"},"post":{"tags":["App Deployments"],"summary":"Create App Deployment","description":"Queue a deployment from a pinned source ref.\n\nReturns `queued`. Nothing builds yet -- the provisioner (M6-8) is what moves\nit to `building`. Recording the intent before any infrastructure exists is\ndeliberate: it makes the control plane the source of truth for what SHOULD be\nrunning, which is what a reconciler needs to exist against.","operationId":"create_app_deployment_apps__app_id__deployments_post","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateDeploymentRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeploymentResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"active"}},"/apps/{app_id}/deployments/active":{"get":{"tags":["App Deployments"],"summary":"Get Active Deployment","description":"What is serving traffic right now, or null.\n\nnull rather than 404 when nothing is deployed: \"this app has never shipped\"\nis an answer, and a 404 would read as \"no such app\".","operationId":"get_active_deployment_apps__app_id__deployments_active_get","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Union_DeploymentResponse__NoneType__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"active"}},"/apps/{app_id}/deployments/{deployment_id}":{"get":{"tags":["App Deployments"],"summary":"Get Deployment","description":"Fetch one deployment.\n\nPolling a build is the most common loop in a deploy flow, and without this it\nrequired listing every deployment and filtering client-side.\n\nREGISTERED AFTER `GET /{app_id}/deployments/active`, and the order is\nload-bearing rather than cosmetic. Both are three segments with a literal or a\nparameter in the same position, so declaring this first would capture `active`\nas a deployment id and that endpoint would 404 for everyone. `GET\n/workflows/dispositions` spent months doing exactly that in production.\n\n404 rather than 403 for a deployment belonging to someone else's app, because\na 403 confirms the id exists. `_own_deployment` is the only way this module\nloads one, so a new route cannot skip the ownership check without also having\nnothing to work with.","operationId":"get_deployment_apps__app_id__deployments__deployment_id__get","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"deployment_id","in":"path","required":true,"schema":{"type":"string","title":"Deployment Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeploymentResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"active"}},"/apps/{app_id}/deployments/{deployment_id}/status":{"post":{"tags":["App Deployments"],"summary":"Report Deployment Progress","description":"The build controller reports progress. THE KEYSTONE (M9 item J2).\n\nWithout this, every deploy route below is inert. `POST /deployments` writes\n`queued`, and the state machine allows `queued -> building -> promoting ->\ndeployed`. Nothing anywhere wrote `building` or `promoting`, so promote asked\nfor `queued -> deployed`, which is illegal, and **every real deployment that\nhas ever existed 409s on promote** while `deployments/active` returns null for\nevery builder.\n\nAUTHENTICATED AS THE CONTROLLER, NOT THE BUILDER, and that is the whole point.\nA builder's own key must not be able to walk their deployment to `promoting`\nwith no build having run, then promote it: the machine would read green and\nthe image would be whatever was there before, or nothing. So this route takes\nno `user` at all. See `dependencies/build_controller_auth.py`.\n\n`deployed` IS NOT SETTABLE HERE. The controller knows when a build finished; it\ndoes not decide the app should take traffic. That is promote, a separate act\nby the builder. Collapsing them would let whichever pod ran the build put an\napp in front of users.\n\n409 on an illegal transition rather than a silent no-op, so a controller that\nreports out of order learns it rather than leaving a deployment wedged in a\nstate nobody wrote.\n\n404 for an unknown deployment, and 404 for a wrong or absent controller token,\ndeliberately indistinguishable. The controller is not a tenant and has no org,\nso there is no ownership check to make here: the deployment id is resolved\nagainst the control plane rather than trusted, and it is the only thing this\ncredential can act on.","operationId":"report_deployment_progress_apps__app_id__deployments__deployment_id__status_post","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"deployment_id","in":"path","required":true,"schema":{"type":"string","title":"Deployment Id"}},{"name":"x-build-controller-token","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Build-Controller-Token"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeploymentProgressRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeploymentResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-lifecycle":"active"}},"/apps/{app_id}/deployments/{deployment_id}/promote":{"post":{"tags":["App Deployments"],"summary":"Promote Deployment","description":"Promote a built deployment to serve traffic.\n\n409 when the state machine forbids it -- a deployment cannot become\n`deployed` without having been built, and a `failed` one cannot be revived.","operationId":"promote_deployment_apps__app_id__deployments__deployment_id__promote_post","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"deployment_id","in":"path","required":true,"schema":{"type":"string","title":"Deployment Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PromoteDeploymentRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeploymentResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"active"}},"/apps/{app_id}/deployments/{deployment_id}/rollback":{"post":{"tags":["App Deployments"],"summary":"Rollback Deployment","description":"Roll back a deployment that is currently serving.\n\nOnly a `deployed` deployment may be rolled back. Rolling back one that never\nserved is meaningless, and permitting it would let a builder mark a failed\nbuild `rolled_back` and hide the failure.","operationId":"rollback_deployment_apps__app_id__deployments__deployment_id__rollback_post","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"deployment_id","in":"path","required":true,"schema":{"type":"string","title":"Deployment Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeploymentResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"active"}},"/apps/{app_id}/deployments/{deployment_id}/logs":{"get":{"tags":["App Logs"],"summary":"Get Deployment Logs","description":"Why a build failed.\n\nReturns every step of the build pod in the order Kubernetes runs them --\nfetch, scan-source, build, scan-image, then push -- because \"which step\" is\nmost of the answer. A step that has not started is omitted rather than\nreturned empty, so a build in progress reports what exists so far.\n\nAn empty `containers` list means the build pod is gone or was never created.\nBuild pods are reaped an hour after they finish (`ttlSecondsAfterFinished`),\nso logs for an older deployment are genuinely unavailable rather than hidden;\n`last_error_sanitized` on the deployment is what survives.\n\n`redacted` is always true and means graph8's credential patterns were applied.\nIt is NOT a claim the output is safe to publish: this is a customer's own\nbuild output and it can print a secret in a shape no pattern matches.","operationId":"get_deployment_logs_apps__app_id__deployments__deployment_id__logs_get","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"deployment_id","in":"path","required":true,"schema":{"type":"string","title":"Deployment Id"}},{"name":"tail_lines","in":"query","required":false,"schema":{"type":"integer","maximum":2000,"minimum":1,"description":"Lines per build step, newest last.","default":200,"title":"Tail Lines"},"description":"Lines per build step, newest last."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppLogsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"active"}},"/apps/{app_id}/logs":{"get":{"tags":["App Logs"],"summary":"Get App Logs","description":"What the running app is printing.\n\nThe app's own pods only. The per-app egress proxy runs in the same namespace\nand is deliberately excluded: it is platform infrastructure that happens to\nlive inside a tenant boundary, and its output is graph8's, not the builder's.\n\nEmpty until a deployment reaches `deployed`. The `app` Deployment ships with\n`replicas: 0` and a pause image, so a namespace that exists still has no app\npod to read until a build has been promoted.","operationId":"get_app_logs_apps__app_id__logs_get","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"tail_lines","in":"query","required":false,"schema":{"type":"integer","maximum":2000,"minimum":1,"description":"Lines per replica, newest last.","default":200,"title":"Tail Lines"},"description":"Lines per replica, newest last."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppLogsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"active"}},"/apps/{app_id}/domains":{"get":{"tags":["App Domains"],"summary":"List App Domains","description":"Every hostname claimed for this app, whatever its verification state.","operationId":"list_app_domains_apps__app_id__domains_get","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_DomainResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"active"},"post":{"tags":["App Domains"],"summary":"Claim App Domain","description":"Claim a hostname and return the TXT record proving you control it.\n\n409 when another app already holds the host. Hostnames are globally unique,\nand a silent overwrite would let one builder take another's traffic -- which\nis why `claim_domain` raises rather than upserting.","operationId":"claim_app_domain_apps__app_id__domains_post","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ClaimDomainRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DomainVerificationInstructions_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"active"}},"/apps/{app_id}/domains/{hostname}/verify":{"post":{"tags":["App Domains"],"summary":"Verify App Domain","description":"Check DNS for the TXT record and advance the domain to `verified`.\n\nIdempotent: verifying an already-verified domain re-checks and stays verified,\nso a builder can re-run it after a DNS change without a special path.","operationId":"verify_app_domain_apps__app_id__domains__hostname__verify_post","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"hostname","in":"path","required":true,"schema":{"type":"string","title":"Hostname"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DomainResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"active"}},"/apps/{app_id}/domains/{hostname}":{"delete":{"tags":["App Domains"],"summary":"Release App Domain","description":"Release a claimed hostname.\n\nHostnames are globally unique across every app\n(``uq_developer_app_domains_hostname``), so one typo permanently burned that\nhost for every builder on the platform with no public way to undo it. The\nrepository had get, list, claim and set_status, and no delete at all.\n\nA HARD delete, not a `revoked` status. The uniqueness index does not care\nabout status, so a row left behind in any state keeps the host claimed while\nlooking to the builder like it was released.\n\nOWNERSHIP IS CHECKED AGAINST THE STORED CLAIM, not just the app in the path.\n`_require_own_app` proves the caller owns THIS app; the second check proves\nthe hostname belongs to that same app. Without it a builder could pass their\nown app id and any hostname, and delete a competitor's claim -- the one thing\nglobal uniqueness makes irreversible.\n\n404 for an unknown host or one held by another app, never 403: a 403 would\nmake a competitor's claim discoverable by probing.\n\nIdempotent within your own app: releasing a host you have already released is\na 404, because after the first call the claim genuinely does not exist. The\ndelete itself reports whether a row went, and both answers are correct.","operationId":"release_app_domain_apps__app_id__domains__hostname__delete","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"hostname","in":"path","required":true,"schema":{"type":"string","title":"Hostname"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"apps:delete","x-graph8-lifecycle":"active"}},"/app-platform/tls-authorize":{"get":{"tags":["App Domains"],"summary":"Tls Authorize","description":"Caddy on-demand-TLS ask endpoint. PUBLIC, UNAUTHENTICATED, FAILS CLOSED.\n\nCaddy issues a certificate when this returns 2xx. Answering 2xx for a host we\ndo not own would let anyone who points DNS at our edge have a publicly\ntrusted certificate minted by us.\n\n2xx ONLY for a hostname that exists AND is `verified`. Everything else is a\nbare 404 with no body: distinguishing \"unknown\" from \"known but unverified\"\nwould make this a free oracle for which customers are onboarding.\n\nIt IS published in the contract. `include_in_schema=False` was the first\ninstinct -- it is infrastructure plumbing, not a customer API -- and it broke\nan invariant: the operation manifest is derived from the OpenAPI spec while\n`operation_tiers` is derived from the route table, so hiding a route makes\nthe two span different universes.\n`test_the_manifest_covers_the_WHOLE_operation_universe` exists to catch\nexactly that, and it went red on qa.\n\nHiding it was never a security control anyway -- the endpoint fails closed on\nits own, and its existence is inferable from any Caddy config. Consistency\nbetween the published contract and the route table is worth more than the\ntidiness of an unlisted endpoint.","operationId":"tls_authorize_app_platform_tls_authorize_get","parameters":[{"name":"domain","in":"query","required":true,"schema":{"type":"string","maxLength":253,"title":"Domain"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-lifecycle":"active"}},"/app/objects":{"get":{"tags":["App Objects"],"summary":"List App Objects","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nList the object types this app declared, in the tenant it is acting for.","operationId":"list_app_objects_app_objects_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"Origin","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Origin"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_ObjectDefinitionResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-lifecycle":"preview","x-graph8-enabled-by":"M6_APP_TOKENS_ENABLED"}},"/app/objects/{object_slug}":{"get":{"tags":["App Objects"],"summary":"Get App Object","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nFetch one of this app's object types.","operationId":"get_app_object_app_objects__object_slug__get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"Origin","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Origin"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectDefinitionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-lifecycle":"preview","x-graph8-enabled-by":"M6_APP_TOKENS_ENABLED"}},"/app/objects/{object_slug}/attributes":{"get":{"tags":["App Objects"],"summary":"List App Object Attributes","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nThe object's attributes — the schema its records must satisfy.","operationId":"list_app_object_attributes_app_objects__object_slug__attributes_get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"Origin","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Origin"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_AttributeDefinitionResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-lifecycle":"preview","x-graph8-enabled-by":"M6_APP_TOKENS_ENABLED"}},"/app/objects/{object_slug}/records":{"get":{"tags":["App Objects"],"summary":"List App Object Records","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nList this app's records in the tenant it is acting for. Archived excluded.","operationId":"list_app_object_records_app_objects__object_slug__records_get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (ignored when `cursor` is supplied)","default":1,"title":"Page"},"description":"Page number (ignored when `cursor` is supplied)"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page","default":50,"title":"Limit"},"description":"Items per page"},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Opaque cursor from a prior response. Takes precedence over `page`.","title":"Cursor"},"description":"Opaque cursor from a prior response. Takes precedence over `page`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"Origin","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Origin"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_ObjectRecordResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-lifecycle":"preview","x-graph8-enabled-by":"M6_APP_TOKENS_ENABLED"},"post":{"tags":["App Objects"],"summary":"Create App Object Record","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nCreate a record in the tenant this app is acting for.\n\nUnknown fields are rejected with 422, not dropped, and every problem comes\nback at once. A collision on a unique attribute is 409.","operationId":"create_app_object_record_app_objects__object_slug__records_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"Origin","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Origin"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RecordWriteRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectRecordResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-lifecycle":"preview","x-graph8-enabled-by":"M6_APP_TOKENS_ENABLED"}},"/app/objects/{object_slug}/records/{record_id}":{"get":{"tags":["App Objects"],"summary":"Get App Object Record","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nFetch one record with its currently active values.","operationId":"get_app_object_record_app_objects__object_slug__records__record_id__get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"record_id","in":"path","required":true,"schema":{"type":"string","title":"Record Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"Origin","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Origin"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectRecordResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-lifecycle":"preview","x-graph8-enabled-by":"M6_APP_TOKENS_ENABLED"},"patch":{"tags":["App Objects"],"summary":"Update App Object Record","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nUpdate a record. Only the supplied attributes are touched.\n\nAn explicit `null` clears an attribute; omitting the key leaves it alone.\nValues are versioned rather than overwritten.","operationId":"update_app_object_record_app_objects__object_slug__records__record_id__patch","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"record_id","in":"path","required":true,"schema":{"type":"string","title":"Record Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"Origin","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Origin"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RecordUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectRecordResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-lifecycle":"preview","x-graph8-enabled-by":"M6_APP_TOKENS_ENABLED"}},"/app/objects/{object_slug}/records/{record_id}/restore":{"post":{"tags":["App Objects"],"summary":"Restore App Object Record","description":"Restore this app's archived record using current constraints and its original ID.","operationId":"restore_app_object_record_app_objects__object_slug__records__record_id__restore_post","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"record_id","in":"path","required":true,"schema":{"type":"string","title":"Record Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"Origin","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Origin"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ObjectRecordResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-lifecycle":"active"}},"/app/objects/{object_slug}/records/{record_id}/history":{"get":{"tags":["App Objects"],"summary":"Get App Object Record History","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nA record's value timeline, newest first.","operationId":"get_app_object_record_history_app_objects__object_slug__records__record_id__history_get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"record_id","in":"path","required":true,"schema":{"type":"string","title":"Record Id"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"description":"Maximum generations to return","default":100,"title":"Limit"},"description":"Maximum generations to return"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"Origin","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Origin"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RecordHistoryResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-lifecycle":"preview","x-graph8-enabled-by":"M6_APP_TOKENS_ENABLED"}},"/app/objects/{object_slug}/records/{record_id}/changes":{"get":{"tags":["App Objects"],"summary":"Get App Object Record Changes","description":"Read mutation facts within the authenticated app and client namespace.","operationId":"get_app_object_record_changes_app_objects__object_slug__records__record_id__changes_get","parameters":[{"name":"object_slug","in":"path","required":true,"schema":{"type":"string","title":"Object Slug"}},{"name":"record_id","in":"path","required":true,"schema":{"type":"string","title":"Record Id"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":100,"title":"Limit"}},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":512},{"type":"null"}],"title":"Cursor"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"Origin","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Origin"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RecordMutationsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-lifecycle":"active"}},"/installed-apps":{"get":{"tags":["Installed Apps"],"summary":"List Installed Apps","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nList the apps installed in your workspace, including revoked ones.\n\nRevoked installs are included on purpose: \"we used to have this app and\nturned it off\" is a different answer from \"we never had it\", and only one of\nthem explains why the app's data is still here.","operationId":"list_installed_apps_installed_apps_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_InstalledAppResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"preview"},"post":{"tags":["Installed Apps"],"summary":"Install App","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nInstall an app into your workspace and grant it scopes.\n\nConsent is recorded immediately — there is no pending step in the beta, and a\n`pending` status that nothing ever advanced would be a trap. Re-installing an\napp you already have UPDATES the grant in place, which is how you change\nscopes; there is exactly one install row per (app, workspace).","operationId":"install_app_installed_apps_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/InstallAppRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InstalledAppResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"preview"}},"/installed-apps/{app_id}":{"get":{"tags":["Installed Apps"],"summary":"Get Installed App","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nOne app's installation in your workspace, and the scopes you granted it.","operationId":"get_installed_app_installed_apps__app_id__get","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InstalledAppResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"preview"},"delete":{"tags":["Installed Apps"],"summary":"Uninstall App","description":"PREVIEW. This endpoint is deployed but gated: it returns 404 unless the hosted app platform is enabled for your organization. It is published here so the contract describes the whole surface, not so it can be called today.\n\nRevoke an app's access to your workspace.\n\nTakes effect on the app's NEXT request, not when its tokens expire: the\nverifier re-resolves consent live, and the M6-1d clamp reads only `consented`\nrows.\n\nYour data is NOT deleted. D13 requires a workspace to keep records an app\nauthored after it is uninstalled — they are yours, and you can still read\nthem through your own API key.","operationId":"uninstall_app_installed_apps__app_id__delete","parameters":[{"name":"app_id","in":"path","required":true,"schema":{"type":"string","title":"App Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InstalledAppResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"apps:delete","x-graph8-lifecycle":"preview"}},"/deals/columns":{"get":{"tags":["Deals"],"summary":"List Deal Columns","description":"The custom columns the deals grid can show.\n\nThe source of the keys `PUT /deals/{id}/columns/values` accepts - writing\nto anything else is refused.","operationId":"list_deal_columns_deals_columns_get","parameters":[{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Only columns scoped to this list, plus the global ones. Omit for the global set alone.","title":"List Id"},"description":"Only columns scoped to this list, plus the global ones. Omit for the global set alone."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/deals/columns/create":{"post":{"tags":["Deals"],"summary":"Create Deal Column","description":"Add a custom column.\n\n`list_id` null creates a GLOBAL column, visible on every deals grid in the\norg. That is the wider blast radius of the two, so it is what you get by\nomission only because it is the app's own default.\n\nThe path is `/columns/create` rather than a POST to `/columns`, matching\nthe app exactly - a different spelling here would be a second way to say\nthe same thing.","operationId":"create_deal_column_deals_columns_create_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateDealColumnRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/deals/columns/{column_id}":{"delete":{"tags":["Deals"],"summary":"Delete Deal Column","description":"Remove a custom column, and the values every deal held in it.","operationId":"delete_deal_column_deals_columns__column_id__delete","parameters":[{"name":"column_id","in":"path","required":true,"schema":{"type":"integer","description":"Column id.","title":"Column Id"},"description":"Column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"deals:delete","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/columns/values":{"put":{"tags":["Deals"],"summary":"Set Deal Column Values","description":"Write custom column values on one deal.\n\nA null CLEARS that column rather than leaving it alone. Keys come from\n`GET /deals/columns`; anything else is refused.","operationId":"set_deal_column_values_deals__deal_id__columns_values_put","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Resolve list-scoped columns against this list.","title":"List Id"},"description":"Resolve list-scoped columns against this list."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetDealColumnValuesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/deals/bulk":{"post":{"tags":["Deals"],"summary":"Bulk Update Deals","description":"Apply ONE change to up to 100 deals.\n\nPUT semantics on every field of `change`: null leaves a value alone, an\nEMPTY STRING clears it. Omitting a field and sending `\"\"` are therefore\ndifferent instructions and the second one is destructive.\n\nRead the per-deal result rather than the HTTP status: a deal the caller\ncannot write is reported, not fatal.","operationId":"bulk_update_deals_deals_bulk_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BulkDealUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/history":{"get":{"tags":["Deals"],"summary":"List Deal History","description":"What changed on this deal, and who changed it.","operationId":"list_deal_history_deals__deal_id__history_get","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"The app's cap, and it is a real ceiling rather than a default to raise: a long history pages through `offset`.","default":200,"title":"Limit"},"description":"The app's cap, and it is a real ceiling rather than a default to raise: a long history pages through `offset`."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealCollectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/rival-attach":{"post":{"tags":["Deals"],"summary":"Set Rival Attach","description":"Record which competitor is on this deal, and how it is going.\n\nA null `competitor_id` DETACHES the current one - the same route both\nattaches and clears.","operationId":"set_rival_attach_deals__deal_id__rival_attach_post","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RivalAttachRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/crossfire":{"get":{"tags":["Deals"],"summary":"Get Deal Crossfire","description":"Competitive pressure on this deal.\n\nOpen-shaped: this is an ADVISORY read whose contents grow with the\nproduct, and a dropped field reads as \"nothing to worry about\" rather than\n\"we did not tell you\".","operationId":"get_deal_crossfire_deals__deal_id__crossfire_get","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id (UUID).","title":"Deal Id"},"description":"Deal id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/merge/preview":{"get":{"tags":["Deals"],"summary":"Preview Deal Merge","description":"What the merge WOULD do. Changes nothing.\n\nWorth calling first for the same reason the app does: merging is not\nreversible, and this is the only place that says which field values change\nand which records move before they do.","operationId":"preview_deal_merge_deals__deal_id__merge_preview_get","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"The deal that SURVIVES.","title":"Deal Id"},"description":"The deal that SURVIVES."},{"name":"secondary","in":"query","required":true,"schema":{"type":"string","description":"The deal that would be merged AWAY.","title":"Secondary"},"description":"The deal that would be merged AWAY."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/merge":{"post":{"tags":["Deals"],"summary":"Merge Deal","description":"Merge `secondary_id` into this deal. NOT REVERSIBLE.\n\nThe secondary deal stops existing; its contacts, notes and activity move\nonto the survivor. `field_overrides` is the only way to keep a value from\nthe deal being merged away.\n\nPreview it first. There is no unmerge.","operationId":"merge_deal_deals__deal_id__merge_post","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"The deal that SURVIVES.","title":"Deal Id"},"description":"The deal that SURVIVES."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MergeDealRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"deals:delete","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/deals":{"post":{"tags":["Deals"],"summary":"Create Account Deal","description":"Create a deal already attached to an account.\n\n`POST /deals` creates one standalone; this attaches it in the same call,\nclosing the window where a deal exists with no account.\n\nNo per-record gate, matching the app: there is no existing deal to check\nagainst, and the account is validated by the handler.","operationId":"create_account_deal_accounts__account_id__deals_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"Account the deal belongs to.","title":"Account Id"},"description":"Account the deal belongs to."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AccountDealCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"},"get":{"tags":["Deals"],"summary":"List Account Deals","description":"Deals on one account.\n\nNo per-record gate: a LIST is filtered by `deal_scope`, which the app\nhandler takes as a parameter and applies itself. Gating row by row here\nwould be both redundant and wrong - there is no single deal id to check.","operationId":"list_account_deals_accounts__account_id__deals_get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"Account id.","title":"Account Id"},"description":"Account id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/pipeline":{"put":{"tags":["Deals"],"summary":"Move Deal To Pipeline","description":"Move a deal into a different pipeline.\n\nThe deal keeps its identity and history. Its STAGE does not carry over -\nthe target pipeline has its own stages and the app re-seats the deal within\nthem, so a caller should read the deal back rather than assume its stage.\n\nThe path is `/pipeline` rather than the app's `/move-pipeline`: the verb is\nalready in the PUT.","operationId":"move_deal_to_pipeline_deals__deal_id__pipeline_put","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id.","title":"Deal Id"},"description":"Deal id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DealMovePipelineRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealOpResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/company":{"put":{"tags":["Deals"],"summary":"Set Deal Company","description":"Attach or change the company on a deal.\n\n`mashup_company_id` is the CANONICAL company id, not a\n`cb_company_extensions` / ABM overlay id. They are different tables with\ndifferent ids, and the wrong one attaches the deal to nothing.","operationId":"set_deal_company_deals__deal_id__company_put","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id.","title":"Deal Id"},"description":"Deal id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DealCompanyRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealOpResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/notes/{note_id}":{"put":{"tags":["Deals"],"summary":"Update Deal Note","description":"Rewrite a note.\n\n`content` is a full REPLACEMENT, not a patch, and `mentioned_users` is who\nis mentioned AFTER the edit - omitting someone removes their mention. Send\nthe whole state you want, not the delta.","operationId":"update_deal_note_deals__deal_id__notes__note_id__put","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id.","title":"Deal Id"},"description":"Deal id."},{"name":"note_id","in":"path","required":true,"schema":{"type":"string","description":"Note id.","title":"Note Id"},"description":"Note id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DealNoteUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealOpResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Deals"],"summary":"Delete Deal Note","description":"Delete a note. The deal and its other notes are untouched.","operationId":"delete_deal_note_deals__deal_id__notes__note_id__delete","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id.","title":"Deal Id"},"description":"Deal id."},{"name":"note_id","in":"path","required":true,"schema":{"type":"string","description":"Note id.","title":"Note Id"},"description":"Note id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealOpResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"deals:delete","x-graph8-lifecycle":"active"}},"/deals/close-reasons":{"get":{"tags":["Deals"],"summary":"List Deal Close Reasons","description":"The org's close reasons, and what this caller may do with them.\n\n`can_manage` comes back WITH the list, resolved by the same rule the\narchive endpoint enforces - the app does that deliberately so the control a\nUI renders and the permission the endpoint applies cannot drift. A\nrebuilder without it has to guess which rows are removable.\n\nLITERAL PATH: registered before `deals_router` so `/deals/{deal_id}` cannot\nread \"close-reasons\" as a deal id.","operationId":"list_deal_close_reasons_deals_close_reasons_get","parameters":[{"name":"kind","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter to one list, e.g. won or lost.","title":"Kind"},"description":"Filter to one list, e.g. won or lost."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CloseReasonListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"post":{"tags":["Deals"],"summary":"Create Deal Close Reason","description":"Add a close reason.\n\nENTRY GATE: `_REASON_MUTATE_PERMISSIONS`, the SAME route dependency the app\ndeclares - wider than the manager tier (a rep may extend the list inline\nwhile closing their own deal) but NOT open to org members with no deal\naccess. `can_manage` is still resolved for the handler; `may_seed` is now\nenforced by the route gate rather than discarded.","operationId":"create_deal_close_reason_deals_close_reasons_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CloseReasonCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealOpResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/deals/close-reasons/{reason_id}":{"delete":{"tags":["Deals"],"summary":"Archive Deal Close Reason","description":"Archive a close reason.\n\nENTRY GATE: `_REASON_MUTATE_PERMISSIONS`, the SAME route dependency the app\ndeclares. Beyond the gate the decision is CREATOR OR MANAGER, not\nmanager-only - the app's own note: manager-only removal \"would make every\nrep's typo permanent and org-wide, in a list\" a rep is expected to extend\ninline. `can_manage` (forwarded to the app handler) enforces that in-body\ncreator-or-manager check, and tells a caller in advance which rows they may\nremove.","operationId":"archive_deal_close_reason_deals_close_reasons__reason_id__delete","parameters":[{"name":"reason_id","in":"path","required":true,"schema":{"type":"string","description":"Close reason id.","title":"Reason Id"},"description":"Close reason id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"deals:delete","x-graph8-lifecycle":"active"}},"/deals/custom-fields/di-config":{"post":{"tags":["Deals"],"summary":"Upsert Deal Custom Field Di Config","description":"Replace the deal custom-field mappings.\n\nENTRY GATE: manager tier (DEALS_WRITE_TEAM / DEALS_WRITE_ALL /\nDEALS_MANAGE), the SAME route dependency the app declares - the values here\nare interpolated into the Deal Intelligence LLM prompt, so an own-scope rep\nmust not be able to poison org-wide DI. The coarse `deals:write` scope does\nnot distinguish own/team/all/manage, so this RBAC gate is what stops a\nrep-minted key reaching a manager-only surface.\n\n`items` is the FULL desired set for the providers it names, not a delta -\nthe app upserts exactly what is sent. The READ half of this pair shipped in\n#20744; this completes it.","operationId":"upsert_deal_custom_field_di_config_deals_custom_fields_di_config_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CustomFieldDiConfigUpsertRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealOpResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"},"get":{"tags":["Deals"],"summary":"List Deal Custom Field Di Config","description":"Which deal custom fields exist and how they map outward.\n\nNo per-record gate: this is org-level configuration, not a deal.\n\nNOTE ON ROUTING ORDER: this path is LITERAL and would otherwise be\nswallowed by `/deals/{deal_id}` in the existing deals router, which would\nread \"custom-fields\" as a deal id. That is why this router is registered\nBEFORE it in `app.py` - see the comment there.","operationId":"list_deal_custom_field_di_config_deals_custom_fields_di_config_get","parameters":[{"name":"crm_provider","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter to one CRM provider's mappings.","title":"Crm Provider"},"description":"Filter to one CRM provider's mappings."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CustomFieldDiConfigListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/detail":{"get":{"tags":["Deals"],"summary":"Get Deal Detail","description":"The full deal record the detail page reads.","operationId":"get_deal_detail_deals__deal_id__detail_get","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id.","title":"Deal Id"},"description":"Deal id."},{"name":"include_revision","in":"query","required":false,"schema":{"type":"boolean","description":"Include the optimistic-concurrency revision. Null in the response means this org has no revision tracking, so a save is unconditional - it does NOT mean revision 1.","default":false,"title":"Include Revision"},"description":"Include the optimistic-concurrency revision. Null in the response means this org has no revision tracking, so a save is unconditional - it does NOT mean revision 1."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/signals":{"get":{"tags":["Deals"],"summary":"Get Deal Signals","description":"Intent and activity signals attached to this deal.\n\nReturned as an open object rather than a pinned shape: the signals payload\nis assembled from several upstreams and declaring a schema here would\nsilently DROP a signal type the moment one is added.","operationId":"get_deal_signals_deals__deal_id__signals_get","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id.","title":"Deal Id"},"description":"Deal id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/contacts":{"get":{"tags":["Deals"],"summary":"List Deal Contacts","description":"Everyone linked to this deal, with their role on it.","operationId":"list_deal_contacts_deals__deal_id__contacts_get","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id.","title":"Deal Id"},"description":"Deal id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealContactListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"post":{"tags":["Deals"],"summary":"Add Deal Contact","description":"Link a contact to this deal.","operationId":"add_deal_contact_deals__deal_id__contacts_post","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id.","title":"Deal Id"},"description":"Deal id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DealContactCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealContact_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/contacts/{person_id}/primary":{"put":{"tags":["Deals"],"summary":"Set Primary Deal Contact","description":"Make this person the deal's primary contact.\n\nA deal has ONE primary, so this demotes whoever held it - there is no\nseparate call to unset the previous one.","operationId":"set_primary_deal_contact_deals__deal_id__contacts__person_id__primary_put","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id.","title":"Deal Id"},"description":"Deal id."},{"name":"person_id","in":"path","required":true,"schema":{"type":"string","description":"Contact id to make primary.","title":"Person Id"},"description":"Contact id to make primary."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealContact_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/contacts/{person_id}":{"delete":{"tags":["Deals"],"summary":"Remove Deal Contact","description":"Unlink a contact from the deal. The contact record itself is untouched.","operationId":"remove_deal_contact_deals__deal_id__contacts__person_id__delete","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id.","title":"Deal Id"},"description":"Deal id."},{"name":"person_id","in":"path","required":true,"schema":{"type":"string","description":"Contact id.","title":"Person Id"},"description":"Contact id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"deals:delete","x-graph8-lifecycle":"active"}},"/desk/batch":{"get":{"tags":["Desk"],"summary":"Get Desk Batch","description":"This rep's batch for their local day.\n\n`data` is NULL when no batch has been started today. That is different\nfrom a batch with nothing left in it, and the difference decides whether a\nUI shows \"start your day\" or \"you are done\" - so it is preserved rather\nthan flattened into an empty batch.\n\nThe app's `include=overview` composite is deliberately not exposed: it\nreturns a different response shape from the same path, which is a shell\noptimisation rather than a contract a rebuilder should depend on.","operationId":"get_desk_batch_desk_batch_get","parameters":[{"name":"tz_offset","in":"query","required":false,"schema":{"type":"integer","maximum":840,"minimum":-840,"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). A batch is scoped to the rep's local day; a wrong offset silently returns the wrong day rather than erroring.","default":0,"title":"Tz Offset"},"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). A batch is scoped to the rep's local day; a wrong offset silently returns the wrong day rather than erroring."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Union_DeskBatch__NoneType__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/batch/start":{"post":{"tags":["Desk"],"summary":"Start Desk Batch","description":"Freeze a ranked slice of the queue into today's batch.\n\nThis is what makes the day finite. Cards added to the queue afterwards do\nNOT join the batch on their own - use `/batch/pull` to take more.","operationId":"start_desk_batch_desk_batch_start_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeskBatchStartRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskBatch_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/desk/batch/pull":{"post":{"tags":["Desk"],"summary":"Pull Desk Batch","description":"Append more cards to today's existing batch.\n\nCapped lower than `start` (40 vs 80) on purpose: pulling is a top-up, not\na second day.","operationId":"pull_desk_batch_desk_batch_pull_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeskBatchPullRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskBatch_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/desk/decisions":{"get":{"tags":["Desk"],"summary":"List Desk Decisions","description":"This rep's pending queue, ranked.\n\n`source_group` and `source` are a family/exact pair, not synonyms:\n`source_group=forms` matches every form signal, `source=form_submitted`\nmatches one.\n\nAn omitted filter is passed as a real `None`. The app's own comment warns\nthat a `Query(None)` sentinel is TRUTHY and would reach the repository as\na filter value - so absent must stay absent all the way down.","operationId":"list_desk_decisions_desk_decisions_get","parameters":[{"name":"decision_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by decision type.","title":"Decision Type"},"description":"Filter by decision type."},{"name":"source_group","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by signal FAMILY, e.g. \"forms\" or \"website\".","title":"Source Group"},"description":"Filter by signal FAMILY, e.g. \"forms\" or \"website\"."},{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by EXACT signal id, e.g. \"form_submitted\".","title":"Source"},"description":"Filter by EXACT signal id, e.g. \"form_submitted\"."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"default":20,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskDecisionListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/decisions/completed":{"get":{"tags":["Desk"],"summary":"List Completed Desk Decisions","description":"What this rep finished today, in their local day.","operationId":"list_completed_desk_decisions_desk_decisions_completed_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"default":20,"title":"Limit"}},{"name":"tz_offset","in":"query","required":false,"schema":{"type":"integer","maximum":840,"minimum":-840,"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). A batch is scoped to the rep's local day; a wrong offset silently returns the wrong day rather than erroring.","default":0,"title":"Tz Offset"},"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). A batch is scoped to the rep's local day; a wrong offset silently returns the wrong day rather than erroring."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskDecisionListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/decisions/{decision_id}/brief":{"get":{"tags":["Desk"],"summary":"Get Desk Decision Brief","description":"Enriched brief for a card - what the slide-over panel shows.\n\nReturned as an open object: the app types this `-> dict` and assembles it\nfrom several upstreams, so pinning a schema here would silently DROP a\nfield the moment one is added.","operationId":"get_desk_decision_brief_desk_decisions__decision_id__brief_get","parameters":[{"name":"decision_id","in":"path","required":true,"schema":{"type":"string","description":"Decision id (UUID).","title":"Decision Id"},"description":"Decision id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/decisions/{decision_id}/card-context":{"get":{"tags":["Desk"],"summary":"Get Desk Decision Card Context","description":"Everything needed to render the card: the entity, its history, the ask.","operationId":"get_desk_decision_card_context_desk_decisions__decision_id__card_context_get","parameters":[{"name":"decision_id","in":"path","required":true,"schema":{"type":"string","description":"Decision id (UUID).","title":"Decision Id"},"description":"Decision id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/decisions/{decision_id}/conversation":{"get":{"tags":["Desk"],"summary":"Get Desk Decision Conversation","description":"The thread behind the card - what has already been said.","operationId":"get_desk_decision_conversation_desk_decisions__decision_id__conversation_get","parameters":[{"name":"decision_id","in":"path","required":true,"schema":{"type":"string","description":"Decision id (UUID).","title":"Decision Id"},"description":"Decision id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/decisions/{decision_id}/resolve":{"post":{"tags":["Desk"],"summary":"Resolve Desk Decision","description":"Resolve a pending card.\n\n`snoozed_until` is REQUIRED when `status=snoozed` - it is the fallback\ntimeout even when `wake_condition` is set, so a snooze can never be\nindefinite. The app enforces that; this surface does not second-guess it,\nit forwards the request and lets the single enforcement point answer.","operationId":"resolve_desk_decision_desk_decisions__decision_id__resolve_post","parameters":[{"name":"decision_id","in":"path","required":true,"schema":{"type":"string","description":"Decision id (UUID).","title":"Decision Id"},"description":"Decision id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeskResolveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/desk/decisions/{decision_id}/undo":{"post":{"tags":["Desk"],"summary":"Undo Desk Decision","description":"Undo an AUTO-EXECUTED decision.\n\nThis is the autopilot escape hatch, not a general undo: it reverses\nsomething the desk did on the rep's behalf. Reversing a card the rep\nresolved themselves is not what this does.","operationId":"undo_desk_decision_desk_decisions__decision_id__undo_post","parameters":[{"name":"decision_id","in":"path","required":true,"schema":{"type":"string","description":"Decision id (UUID).","title":"Decision Id"},"description":"Decision id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/desk/decisions/{decision_id}/unsnooze":{"post":{"tags":["Desk"],"summary":"Unsnooze Desk Decision","description":"Wake a snoozed card now, restoring it to the pending queue.","operationId":"unsnooze_desk_decision_desk_decisions__decision_id__unsnooze_post","parameters":[{"name":"decision_id","in":"path","required":true,"schema":{"type":"string","description":"Decision id (UUID).","title":"Decision Id"},"description":"Decision id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/desk/cards":{"post":{"tags":["Desk"],"summary":"Put one planned outreach touch (an email, LinkedIn or call step for one contact) on a rep's desk with its why, facts and draft. The rep edits and sends it; nothing sends by itself. owner_id must be the caller's own email unless the key is an org or machine key: a personal key or an OAuth connection is a person and gets 403 owner_not_self for anyone else. Posting the same external_key again updates the open card instead of adding a second one. Needs deals:write and a key allowed to see the contact","description":"Put one planned touch on a rep's desk, with its why, facts, fields and draft.\n\n201 when the card is made. The same touch posted again (same\n`external_key`, else the same `list_id` + `contact_id` + `touch`, else the\nsame rep, contact, channel and due day) while the card is unsent answers\n200 with the same `card_id` and `updated: true`. An `external_key` is\nkept apart per `origin.kind`, so two integrations may both use \"1\"; a\nbody with no `origin.kind` shares one namespace with every other such\ncaller in the org, so its key must be unique across the org. Once the rep has sent or\ndecided it, a re-post makes a new card. A card the desk will not make is a\n4xx whose `detail.reason` says why. A personal key may name only its own\nholder (403 `owner_not_self`); an org key may name any active rep.\nThe key must be allowed to see the contact (and the account when one is\nnamed, else the contact's own company), checked the way the contacts and deals routes check a record id\nfrom a body; one it may not see is 403 `contact_not_allowed` /\n`account_not_allowed` and no card is made.","operationId":"create_desk_card_desk_cards_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeskCardCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskCardResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/desk/blocks":{"get":{"tags":["Desk"],"summary":"List Desk Blocks","description":"Dial passes due per list, from the redial ladder over call activity.\n\nA \"block\" is batched calling work: one of the rep's pinned lists, plus how\nmany of its contacts the ladder says are due a call today.","operationId":"list_desk_blocks_desk_blocks_get","parameters":[{"name":"tz_offset","in":"query","required":false,"schema":{"type":"integer","maximum":840,"minimum":-840,"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). The desk day is the rep's LOCAL day; a wrong offset silently returns the wrong day rather than erroring.","default":0,"title":"Tz Offset"},"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). The desk day is the rep's LOCAL day; a wrong offset silently returns the wrong day rather than erroring."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/blocks/{list_id}/queue":{"get":{"tags":["Desk"],"summary":"Get Desk Block Queue","description":"The ordered work set behind one dial block.\n\nAlways 200, including for a list with nothing due - an empty queue is an\nanswer, not an error. The ladder and the ownership rules are applied here,\nwhich is why `/desk/contacts/{contact_id}/call-target` can then resolve a\nnumber for any stop it produced.","operationId":"get_desk_block_queue_desk_blocks__list_id__queue_get","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","description":"Dial list (audience) id.","title":"List Id"},"description":"Dial list (audience) id."},{"name":"redial_only","in":"query","required":false,"schema":{"type":"boolean","description":"Only the contacts whose redial day is up, never the not-yet-called half.","default":false,"title":"Redial Only"},"description":"Only the contacts whose redial day is up, never the not-yet-called half."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/list-priority":{"get":{"tags":["Desk"],"summary":"Get Desk List Priority","description":"The rep's pinned dial lists, most important first.","operationId":"get_desk_list_priority_desk_list_priority_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"put":{"tags":["Desk"],"summary":"Update Desk List Priority","description":"Set the rep's dial-list order. THE WHOLE ORDER.\n\nThis REPLACES the stored order rather than merging into it: sending one id\npins that list and unpins every other, and sending `[]` clears them all.\nThe field name reads like an append, which is exactly why it is said here.","operationId":"update_desk_list_priority_desk_list_priority_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeskListPriorityUpdate"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/desk/list-group-override":{"get":{"tags":["Desk"],"summary":"Get Desk List Group Override","description":"The rep's own moves of dial lists into a band, keyed by list id.","operationId":"get_desk_list_group_override_desk_list_group_override_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"put":{"tags":["Desk"],"summary":"Update Desk List Group Override","description":"Set the rep's band moves. THE WHOLE MAP, not one entry.\n\nPer rep, per org. The stored value is echoed back rather than the submitted\none, so the response is what a GET would return.","operationId":"update_desk_list_group_override_desk_list_group_override_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeskListGroupOverrideUpdate"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/desk/list-goals":{"get":{"tags":["Desk"],"summary":"Get Desk List Goals","description":"The rep's per-list daily dial targets, and progress against them.","operationId":"get_desk_list_goals_desk_list_goals_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"put":{"tags":["Desk"],"summary":"Update Desk List Goal","description":"Set or clear ONE list's daily dial target.\n\nUnlike `/desk/list-priority` this is a single-list edit, and a null\n`target` CLEARS the goal rather than setting it to zero - a cleared goal\nstops the counter, a zero would be a goal that is already met.","operationId":"update_desk_list_goal_desk_list_goals_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeskListGoalUpdate"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/desk/list-goals/{list_id}/revive":{"post":{"tags":["Desk"],"summary":"Revive Desk List Goal","description":"\"I am carrying on today\" - keep dialling past a met goal.\n\nDoes NOT clear or raise the target. The goal stays what it was and stays\nmet; this only stops the desk treating the list as finished for the rest\nof the rep's local day.","operationId":"revive_desk_list_goal_desk_list_goals__list_id__revive_post","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","description":"Dial list (audience) id.","title":"List Id"},"description":"Dial list (audience) id."},{"name":"tz_offset","in":"query","required":false,"schema":{"type":"integer","maximum":840,"minimum":-840,"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). The desk day is the rep's LOCAL day; a wrong offset silently returns the wrong day rather than erroring.","default":0,"title":"Tz Offset"},"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). The desk day is the rep's LOCAL day; a wrong offset silently returns the wrong day rather than erroring."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/desk/pulse":{"get":{"tags":["Desk"],"summary":"Get Desk Pulse","description":"Queue counts, the type breakdown, and the nudge.","operationId":"get_desk_pulse_desk_pulse_get","parameters":[{"name":"tz_offset","in":"query","required":false,"schema":{"type":"integer","maximum":840,"minimum":-840,"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). The desk day is the rep's LOCAL day; a wrong offset silently returns the wrong day rather than erroring.","default":0,"title":"Tz Offset"},"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). The desk day is the rep's LOCAL day; a wrong offset silently returns the wrong day rather than erroring."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/home-summary":{"get":{"tags":["Desk"],"summary":"Get Desk Home Summary","description":"Goal progress, streak, digest and tomorrow's preview, in one read.\n\n`since` narrows the digest lookback in the app. It is not published: it\ndefaults to the last 24 hours, is capped at seven days, and exposing it\nwould publish a knob whose only effect is to skip a 60-second cache.","operationId":"get_desk_home_summary_desk_home_summary_get","parameters":[{"name":"tz_offset","in":"query","required":false,"schema":{"type":"integer","maximum":840,"minimum":-840,"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). The desk day is the rep's LOCAL day; a wrong offset silently returns the wrong day rather than erroring.","default":0,"title":"Tz Offset"},"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). The desk day is the rep's LOCAL day; a wrong offset silently returns the wrong day rather than erroring."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/upcoming":{"get":{"tags":["Desk"],"summary":"List Desk Upcoming","description":"Plan steps beyond the card horizon - what lands after today.\n\nEmpty when nothing is ahead, which is a different statement from an empty\nQUEUE: the queue is what is due now, this is what is coming.","operationId":"list_desk_upcoming_desk_upcoming_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/wrapped":{"get":{"tags":["Desk"],"summary":"Get Desk Wrapped","description":"This local ISO WEEK's numbers, best email and personal records.\n\nWeekly, not daily, and the week boundary follows `tz_offset` - so a wrong\noffset can return last week's numbers around the weekend.","operationId":"get_desk_wrapped_desk_wrapped_get","parameters":[{"name":"tz_offset","in":"query","required":false,"schema":{"type":"integer","maximum":840,"minimum":-840,"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). The desk day is the rep's LOCAL day; a wrong offset silently returns the wrong day rather than erroring.","default":0,"title":"Tz Offset"},"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). The desk day is the rep's LOCAL day; a wrong offset silently returns the wrong day rather than erroring."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/coverage":{"get":{"tags":["Desk"],"summary":"Get Desk Coverage","description":"Quarterly open-pipeline coverage against target.\n\n`{\"enabled\": false}` when the org has set no quarterly target - a 200 with\na reason rather than a 404, so a dashboard can say \"not configured\".","operationId":"get_desk_coverage_desk_coverage_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/compliance-summary":{"get":{"tags":["Desk"],"summary":"Get Desk Compliance Summary","description":"Stage-checklist readiness aggregated across this rep's open deals.","operationId":"get_desk_compliance_summary_desk_compliance_summary_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Open deals to aggregate over.","default":50,"title":"Limit"},"description":"Open deals to aggregate over."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/next-best":{"get":{"tags":["Desk"],"summary":"Get Desk Next Best","description":"Next-best account suggestions. At most three; cached for an hour.","operationId":"get_desk_next_best_desk_next_best_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/committee-heat":{"get":{"tags":["Desk"],"summary":"Get Desk Committee Heat","description":"Four-week engagement heatmap for an account's buying committee.\n\nRead-only and no model call. Fails SOFT to an empty member list rather\nthan erroring, so a dashboard degrades instead of breaking.","operationId":"get_desk_committee_heat_desk_committee_heat_get","parameters":[{"name":"account_id","in":"query","required":true,"schema":{"type":"integer","minimum":1,"description":"The account's mashup company id (`cb_account_plans.account_id`).","title":"Account Id"},"description":"The account's mashup company id (`cb_account_plans.account_id`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/committee-targets":{"get":{"tags":["Desk"],"summary":"Get Desk Committee Targets","description":"Who on the committee is reachable on LinkedIn, and why not when not.\n\nReads only: it never sends and never writes. The send is\n`POST /desk/accounts/{account_id}/committee/{contact_id}/linkedin-invite`.","operationId":"get_desk_committee_targets_desk_committee_targets_get","parameters":[{"name":"account_id","in":"query","required":true,"schema":{"type":"integer","minimum":1,"description":"The account's mashup company id (`cb_account_plans.account_id`).","title":"Account Id"},"description":"The account's mashup company id (`cb_account_plans.account_id`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/kickoff":{"get":{"tags":["Desk"],"summary":"Get Desk Kickoff","description":"The rep's 60-second AI daily briefing, cached per local day.\n\nSPENDS CREDITS ON THE FIRST READ OF THE DAY: a cache miss builds the\nbriefing with a charged model call; every later read that day is served\nfrom the cache. That is why this GET is tiered `billable`, not `read`.\n\n`{\"enabled\": false}` when the org's `morning_kickoff` switch is off.\n\nThe app's `force=true` rebuild is NOT published, and that is a spend\ndecision rather than a tidiness one: the briefing is one model call per rep\nper local day, and a published `force` turns a dashboard poll into a\ncharged call per request. Read the cached one; it is the same briefing the\nrep sees. (`force=False` is passed EXPLICITLY below - the app's default is\na `Query` instance, which is truthy, so omitting it would force a rebuild\non every single call.)","operationId":"get_desk_kickoff_desk_kickoff_get","parameters":[{"name":"tz_offset","in":"query","required":false,"schema":{"type":"integer","maximum":840,"minimum":-840,"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). The desk day is the rep's LOCAL day; a wrong offset silently returns the wrong day rather than erroring.","default":0,"title":"Tz Offset"},"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). The desk day is the rep's LOCAL day; a wrong offset silently returns the wrong day rather than erroring."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/desk/kickoff/played":{"post":{"tags":["Desk"],"summary":"Mark Desk Kickoff Played","description":"Mark today's kickoff as played, so it does not auto-replay.\n\nA 48-hour flag, not a permanent one.","operationId":"mark_desk_kickoff_played_desk_kickoff_played_post","parameters":[{"name":"tz_offset","in":"query","required":false,"schema":{"type":"integer","maximum":840,"minimum":-840,"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). The desk day is the rep's LOCAL day; a wrong offset silently returns the wrong day rather than erroring.","default":0,"title":"Tz Offset"},"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). The desk day is the rep's LOCAL day; a wrong offset silently returns the wrong day rather than erroring."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/desk/kickoff/audio":{"get":{"tags":["Desk"],"summary":"Get Desk Kickoff Audio","description":"Today's kickoff script, SPOKEN: an `audio/mpeg` body.\n\nThe one desk operation that does not answer in the JSON envelope - the\npayload is the MP3 itself, exactly as the app serves it. The script it\nspeaks is `GET /desk/kickoff`. The speech call is platform cost, but the\nscript behind it is BUILT here on a cache miss - a charged model call, the\nsame one `GET /desk/kickoff` makes - so this GET is tiered `billable`.","operationId":"get_desk_kickoff_audio_desk_kickoff_audio_get","parameters":[{"name":"tz_offset","in":"query","required":false,"schema":{"type":"integer","maximum":840,"minimum":-840,"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). The desk day is the rep's LOCAL day; a wrong offset silently returns the wrong day rather than erroring.","default":0,"title":"Tz Offset"},"description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). The desk day is the rep's LOCAL day; a wrong offset silently returns the wrong day rather than erroring."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"The spoken kickoff, as an MP3 body (not the JSON envelope).","content":{"audio/mpeg":{}}},"404":{"description":"Morning Kickoff is off for this org, or speech is unavailable."},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/desk/autonomy":{"get":{"tags":["Desk"],"summary":"Get Desk Autonomy","description":"This rep's autonomy lanes, and which decision types can be automated.\n\n`autopilot_capable_types` is the useful half: a type not in it cannot be\nput on autopilot, and asking for it is silently DOWNGRADED rather than\nrefused, so read this before writing lanes.","operationId":"get_desk_autonomy_desk_autonomy_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"put":{"tags":["Desk"],"summary":"Update Desk Autonomy","description":"Decide what the desk may do WITHOUT asking this rep first.\n\nThis is not a preference. A lane of `autopilot` means the desk executes\nthat decision type on the rep's behalf, and the types that can be automated\ninclude ones that reach a real person - which is why `POST /desk/decisions/\n{id}/undo` exists at all, and why this operation is not tiered a plain\n`write`.\n\n`lanes` MERGES into the stored map rather than replacing it, and a lane\nasking for autopilot on a type with no executor is downgraded rather than\nrefused - so a bulk save echoing back a stale lane still succeeds. An\nomitted `autonomy_families` leaves the family answers alone; an explicit\n`{}` clears them.","operationId":"update_desk_autonomy_desk_autonomy_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeskAutonomyUpdate"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/desk/email-score":{"post":{"tags":["Desk"],"summary":"Score Desk Email","description":"Score a draft 0-100: heuristics for 60%, a model read for 40%.\n\nNever fails for model reasons - with the org's `ai_briefs` switch off, or\nthe model unavailable, it returns the heuristic score alone rather than an\nerror. So a 200 here does not prove the AI half ran.","operationId":"score_desk_email_desk_email_score_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeskEmailScoreRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/desk/email-improve":{"post":{"tags":["Desk"],"summary":"Improve Desk Email","description":"Rewrite a draft, targeting the subscores it is failing.\n\nUnlike `/desk/email-score` this one has no heuristic fallback: it is a\nmodel call or nothing. 400 when the org's `ai_briefs` switch is off, 502\nwhen the model could not answer.","operationId":"improve_desk_email_desk_email_improve_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeskEmailImproveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/desk/ask":{"post":{"tags":["Desk"],"summary":"Ask Desk","description":"Ask a grounded question about a card or a deal.\n\nFAIL-SOFT: with the org's `ai_briefs` switch off it returns a canned answer\nand HTTP 200, not an error. A caller that needs to know whether it got a\nreal answer should look at the payload, not the status code.","operationId":"ask_desk_desk_ask_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeskAskRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/desk/voice-memo":{"post":{"tags":["Desk"],"summary":"Post Desk Voice Memo","description":"SPENDS CREDITS. Transcribe a voice memo and turn it into desk actions.\n\nMultipart, like the app. The memo is transcribed, its actions extracted by\na model, and the result materialised as cards and tasks for this rep - the\ncredits are charged per memo. 400 on an empty upload, 413 over 5 MB, 403\nwhen `deal_id` names a deal this rep may not write, 502 when transcription\nor extraction failed (nothing is materialised then).","operationId":"post_desk_voice_memo_desk_voice_memo_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_post_desk_voice_memo_desk_voice_memo_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/desk/decisions/{decision_id}/replan":{"post":{"tags":["Desk"],"summary":"Replan Desk Decision","description":"SPENDS CREDITS. Gather fresh evidence and write a NEW plan version.\n\nRep-pressed only; nothing automatic reaches this. It rides the org's\nexisting `account_plan_replan` switch, the per-account 24-hour cooldown and\nthe org's daily cap, and a press cannot bypass any of them.\n\nA refusal from a gate is a 409 and costs NOTHING. A failure after the model\nanswered may already have been charged, and says so in the response. There\nis no retry anywhere in this path, so a 409 means stop rather than try\nagain.","operationId":"replan_desk_decision_desk_decisions__decision_id__replan_post","parameters":[{"name":"decision_id","in":"path","required":true,"schema":{"type":"string","description":"Plan-review decision id (UUID).","title":"Decision Id"},"description":"Plan-review decision id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/desk/contacts/{contact_id}/call-target":{"post":{"tags":["Desk"],"summary":"Get Desk Contact Call Target","description":"Resolve the dialable number for one contact, after the opt-out check.\n\nALWAYS 200. \"No number on file\" and \"this person opted out\" are ordinary\nanswers carried in the payload as `is_dialable: false` with a reason, not\nerrors - a caller that treats a non-200 as the only failure mode will dial\npeople who asked not to be called.\n\nPOST rather than GET is the app's choice: it consults the suppression\nledger, and pressing Call is an intent to contact someone, which should not\nbe firable by a prefetch. It resolves and writes nothing, which is why it\nis tiered a READ.","operationId":"get_desk_contact_call_target_desk_contacts__contact_id__call_target_post","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/decisions/{decision_id}/call-target":{"post":{"tags":["Desk"],"summary":"Get Desk Call Target","description":"Resolve the dialable number for a CARD, after the opt-out check.\n\nSame always-200 contract as the contact route above. The difference is\nownership: this one checks the card belongs to the calling rep, because a\ncard names a specific person to call.","operationId":"get_desk_call_target_desk_decisions__decision_id__call_target_post","parameters":[{"name":"decision_id","in":"path","required":true,"schema":{"type":"string","description":"Decision id (UUID).","title":"Decision Id"},"description":"Decision id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/decisions/{decision_id}/reply-target":{"post":{"tags":["Desk"],"summary":"Get Desk Reply Target","description":"Who this card replies TO, and which mailbox it replies FROM.\n\nALWAYS 200: no address on file, no authorised mailbox and an opt-out all\ncome back as `is_sendable: false` with a reason.\n\nResolving is not sending, and this route does neither a write nor a send.\nCall `/desk/decisions/{id}/send-reply` for that - it re-runs the opt-out\ncheck, because this answer is only as fresh as the moment it was asked.","operationId":"get_desk_reply_target_desk_decisions__decision_id__reply_target_post","parameters":[{"name":"decision_id","in":"path","required":true,"schema":{"type":"string","description":"Decision id (UUID).","title":"Decision Id"},"description":"Decision id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/decisions/{decision_id}/sms-target":{"post":{"tags":["Desk"],"summary":"Get Desk Sms Target","description":"Which number this card texts, and which number it texts FROM.\n\nAlways 200, same as the other two targets. Resolves; never sends.","operationId":"get_desk_sms_target_desk_decisions__decision_id__sms_target_post","parameters":[{"name":"decision_id","in":"path","required":true,"schema":{"type":"string","description":"Decision id (UUID).","title":"Decision Id"},"description":"Decision id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/decisions/{decision_id}/send-reply":{"post":{"tags":["Desk"],"summary":"Send Desk Reply","description":"SENDS AN EMAIL to a real person, then resolves the card.\n\nNot idempotent, and it cannot be: the inbox send path carries no request\nid and no dedupe key. What protects a caller instead is the CARD: it is\nclaimed before the send, guarded on still being pending, so only one\nrequest can win and a second gets a 409 having sent nothing.\n\nA retry after a timeout is therefore safe in the usual case and silent in\none: a crash between the claim and the send leaves a resolved card whose\nmail never went. That is deliberate - recoverable by a human, unlike a\nduplicate email, which cannot be recalled.\n\nThe opt-out check runs AGAIN here. `reply-target` already asked, but that\nanswer is as old as the caller's editing session and a STOP that arrived\nmeanwhile must not be sent through.","operationId":"send_desk_reply_desk_decisions__decision_id__send_reply_post","parameters":[{"name":"decision_id","in":"path","required":true,"schema":{"type":"string","description":"Decision id (UUID).","title":"Decision Id"},"description":"Decision id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeskSendReplyRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/desk/decisions/{decision_id}/send-sms":{"post":{"tags":["Desk"],"summary":"Send Desk Sms","description":"SENDS A TEXT MESSAGE to a real phone, then resolves the card.\n\nCarrier spend, and unrecallable once gone. Same claim-then-send ordering\nand the same re-run of the opt-out check as `send-reply` - see that\ndocstring for why a retry is safe and where it is not.","operationId":"send_desk_sms_desk_decisions__decision_id__send_sms_post","parameters":[{"name":"decision_id","in":"path","required":true,"schema":{"type":"string","description":"Decision id (UUID).","title":"Decision Id"},"description":"Decision id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeskSendSmsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/desk/linkedin-sender":{"get":{"tags":["Desk"],"summary":"Get Desk Linkedin Sender","description":"Which LinkedIn account this rep sends desk invites from.\n\nReturns the rep's own pick plus every account in the org and who holds it,\nso a caller can see what is free before claiming one.","operationId":"get_desk_linkedin_sender_desk_linkedin_sender_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"put":{"tags":["Desk"],"summary":"Update Desk Linkedin Sender","description":"Claim a LinkedIn account for this rep, or release the claim with null.\n\nThe claim is EXCLUSIVE and enforced by unique constraints, not by a\npermission: claiming an account a colleague holds is a 409. Sending null\ngives the claim up, which is the only way to hand an account over.\n\nNo admin gate, deliberately, and the app says why: this is a per-user\nidentity rather than an org decision, and an admin permission here would\nstop reps doing the one thing they were told to do.","operationId":"update_desk_linkedin_sender_desk_linkedin_sender_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeskLinkedInSenderUpdate"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/desk/plays/approvals":{"get":{"tags":["Desk"],"summary":"List Desk Play Approvals","description":"Workflow runs THIS rep started that are paused for a human decision.\n\nEmpty list when the org has not enabled plays - this is a read, so a gated\norg gets a quiet 200 empty list rather than a 404 (g8 #19786; the paired\n`decide` action still 404s for a gated org). A reachable-but-unhappy engine\ninstead returns an empty list with `engine_unreachable: true`, so \"nothing\nwaiting\" and \"cannot tell\" are distinguishable rather than both rendering as\na quiet panel.","operationId":"list_desk_play_approvals_desk_plays_approvals_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/plays/approvals/{execution_id}/decide":{"post":{"tags":["Desk"],"summary":"Decide Desk Play Approval","description":"Approve or reject one paused run, AS THIS REP.\n\nApproving RESUMES the run, and what it then does is whatever the workflow\ndoes - which can include sending. The identity matters: the workflow's\nauthor may have named an approver list, and a caller not on it gets a 403\nrather than a silent no-op.\n\n403 means \"not your decision to make\", 404 means the run is no longer\nwaiting. Neither is a retryable error.","operationId":"decide_desk_play_approval_desk_plays_approvals__execution_id__decide_post","parameters":[{"name":"execution_id","in":"path","required":true,"schema":{"type":"string","description":"Paused workflow execution id.","title":"Execution Id"},"description":"Paused workflow execution id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeskApprovalDecisionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/desk/plays/executions/{execution_id}":{"get":{"tags":["Desk"],"summary":"Get Desk Play Execution","description":"Live state of one play run.\n\nPass `decision_id` only if you want the card updated when the run reaches a\nterminal state; that is what the desk's own status chip does as it polls.","operationId":"get_desk_play_execution_desk_plays_executions__execution_id__get","parameters":[{"name":"execution_id","in":"path","required":true,"schema":{"type":"string","description":"Workflow execution id.","title":"Execution Id"},"description":"Workflow execution id."},{"name":"decision_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Card this run belongs to. When given, a TERMINAL status is persisted onto the card - so this read has a write side, and omitting it keeps the read pure.","title":"Decision Id"},"description":"Card this run belongs to. When given, a TERMINAL status is persisted onto the card - so this read has a write side, and omitting it keeps the read pure."},{"name":"action_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Play this run belongs to.","title":"Action Id"},"description":"Play this run belongs to."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/decisions/{decision_id}/plays":{"get":{"tags":["Desk"],"summary":"List Desk Card Plays","description":"Workflows this card can run against its contact or company.\n\n404 when the org has not enabled plays. Each entry carries the effects the\nplay would have in plain words, which is what makes the run below a\ndeliberate act rather than a guess.","operationId":"list_desk_card_plays_desk_decisions__decision_id__plays_get","parameters":[{"name":"decision_id","in":"path","required":true,"schema":{"type":"string","description":"Decision id (UUID).","title":"Decision Id"},"description":"Decision id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/decisions/{decision_id}/plays/{action_id}/run":{"post":{"tags":["Desk"],"summary":"Run Desk Card Play","description":"Run one play against this card's entity. REACHES THE OUTSIDE WORLD.\n\nA play is a workflow, and a workflow can email, send a LinkedIn message or\npush to a third party. That is why this is not a plain write: the grant to\nfire one is the grant to have graph8 act on a customer's behalf.\n\nIDEMPOTENT per (org, card, play) for one hour, so a retried press does not\nfire twice. The play is re-validated against this card's own eligible list,\nso an `action_id` the listing hides cannot be run by posting it directly,\nand the workflow's steps are re-read fresh on every press rather than from\nthe listing's cache.\n\n409 is a refusal, not a failure: the workflow exists and the caller may see\nit, the desk just will not fire it - and nothing has spent at that point.","operationId":"run_desk_card_play_desk_decisions__decision_id__plays__action_id__run_post","parameters":[{"name":"decision_id","in":"path","required":true,"schema":{"type":"string","description":"Decision id (UUID).","title":"Decision Id"},"description":"Decision id (UUID)."},{"name":"action_id","in":"path","required":true,"schema":{"type":"string","description":"Play id, from `/desk/decisions/{id}/plays`.","title":"Action Id"},"description":"Play id, from `/desk/decisions/{id}/plays`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/desk/org-settings":{"get":{"tags":["Desk"],"summary":"Get Desk Org Settings","description":"Effective org-level desk settings: kill switches, thresholds and caps.\n\nUNGATED on purpose, matching the app. This is the always-on desk home read\n(\"watching N signals\"), so requiring `settings:read` would break it for\nevery SDR and AE. The admin surface is the PUT below.","operationId":"get_desk_org_settings_desk_org_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"put":{"tags":["Desk"],"summary":"Update Desk Org Settings","description":"Update org-level desk settings. PARTIAL - unset fields are untouched.\n\nRequires `settings:write`, declared on this route because the app's own\ngate is a `Depends`-defaulted PARAMETER of the handler and a direct call\nresolves nothing.\n\nTHIS IS THE ORG'S ON SWITCH, AND ITS SPEND CAPS. Saving here registers the\norg on the desk worker's poll list - and saving every decision off\nunregisters it - so this one call starts or stops the desk producing work\nfor the whole organisation. It also carries `max_auto_account_plans_per_day`,\n`max_account_replans_per_day` and `max_skill_plans_per_day`, which are\ndaily caps on CHARGED model calls, and `desk_acts_on_signals`,\n`desk_drafts_with_ai` and `stalled_deal_send_email`, which let the desk act\nand email on its own. A plain `write` would make raising an org's spend cap\nthe same grant as renaming a record.\n\n400 with the reason on anything the settings validator refuses, including\nan empty body - \"no settings provided\" is an error here rather than a\nsilent no-op.","operationId":"update_desk_org_settings_desk_org_settings_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeskOrgSettingsUpdate"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/desk/org-settings/plan-stages/check":{"get":{"tags":["Desk"],"summary":"Check Desk Plan Stage Sweep","description":"How many open deals the sweep below WOULD plan, and why the rest not.\n\nSPENDS NOTHING. A GET behind a write permission, which is the app's choice\nand the right one: this exists to be read immediately before the charged\nrun, by the person allowed to fire it.\n\nRead `cap`, `cap_exhausted` and `eligible` before running - they are what\ntell you whether the press will do anything.","operationId":"check_desk_plan_stage_sweep_desk_org_settings_plan_stages_check_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/org-settings/plan-stages/run":{"post":{"tags":["Desk"],"summary":"Run Desk Plan Stage Sweep","description":"CHARGED, AND IT ACTS ON MANY DEALS AT ONCE.\n\nOne model call per plan, capped at 100 credits each, for every open deal\nalready sitting in the org's plan-required stages - stopping at the org's\ndaily cap. That is the difference between this and every other write on\nthe desk: the spend scales with the org's pipeline rather than being one\nunit of work.\n\nCall `/desk/org-settings/plan-stages/check` first; it counts and costs\nnothing. A second press inside the hour buys nothing (the per-deal\ncooldown), and a press while a sweep is running returns\n`stopped: \"already_running\"` having written nothing.","operationId":"run_desk_plan_stage_sweep_desk_org_settings_plan_stages_run_post","parameters":[{"name":"limit","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","maximum":100,"minimum":1},{"type":"null"}],"description":"Plan at most this many deals in this press. Omitted means up to the daily cap.","title":"Limit"},"description":"Plan at most this many deals in this press. Omitted means up to the daily cap."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DeskPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/desk/accounts/plans":{"get":{"tags":["Desk"],"summary":"List Account Plans","description":"The Account Board: the latest plan version per account.\n\n`mine=true` is resolved against the caller's own identity. For a MACHINE\nkey that is nobody, so it returns nothing - which is correct rather than\nbroken, and is why the default is false.","operationId":"list_account_plans_desk_accounts_plans_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"enum":["draft","active","paused","archived"],"type":"string"},{"type":"null"}],"description":"Only plans in this status.","title":"Status"},"description":"Only plans in this status."},{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"enum":["all","deals","campaign"],"type":"string"},{"type":"null"}],"description":"Which board: `deals` (accounts with an open deal), `campaign` (requires `campaign_id`), or `all`. Omitted means all.","title":"Source"},"description":"Which board: `deals` (accounts with an open deal), `campaign` (requires `campaign_id`), or `all`. Omitted means all."},{"name":"campaign_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"REQUIRED when `source=campaign`.","title":"Campaign Id"},"description":"REQUIRED when `source=campaign`."},{"name":"mine","in":"query","required":false,"schema":{"type":"boolean","description":"Only accounts this caller owns. Ownership is resolved BEFORE paging, so this changes the total rather than filtering a page.","default":false,"title":"Mine"},"description":"Only accounts this caller owns. Ownership is resolved BEFORE paging, so this changes the total rather than filtering a page."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":100,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AccountPlanListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/accounts/{account_id}/plan":{"get":{"tags":["Desk"],"summary":"Get Account Plan","description":"The LATEST plan version for this account.","operationId":"get_account_plan_desk_accounts__account_id__plan_get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"The account's mashup company id (`cb_account_plans.account_id`).","title":"Account Id"},"description":"The account's mashup company id (`cb_account_plans.account_id`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AccountPlanPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"post":{"tags":["Desk"],"summary":"Create Or Replan Account Plan","description":"Write this account's plan, from a plan the CALLER authored.\n\nCreate and replan are the same operation because a plan is versioned: this\ninserts a new version and bumps `plan_version` whether or not one existed.\nNothing is generated and nothing is charged - the steps come from the\nrequest body. For the desk to draft them instead, use `/plan/draft`.","operationId":"create_or_replan_account_plan_desk_accounts__account_id__plan_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"The account's mashup company id (`cb_account_plans.account_id`).","title":"Account Id"},"description":"The account's mashup company id (`cb_account_plans.account_id`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AccountPlanUpsertRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AccountPlanPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/desk/accounts/{account_id}/plan/history":{"get":{"tags":["Desk"],"summary":"Get Account Plan History","description":"Every version of this account's plan, newest first.\n\nVersions are immutable, so this is the audit trail: what the plan said\nbefore each replan, and what triggered it.","operationId":"get_account_plan_history_desk_accounts__account_id__plan_history_get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"The account's mashup company id (`cb_account_plans.account_id`).","title":"Account Id"},"description":"The account's mashup company id (`cb_account_plans.account_id`)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":20,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AccountPlanListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/accounts/{account_id}/plan/draft":{"post":{"tags":["Desk"],"summary":"Draft Account Plan","description":"SPENDS CREDITS. Let the desk draft the committee and the first steps.\n\nThis runs the same producer the desk runs automatically, and it counts\nagainst the org's `max_auto_account_plans_per_day` cap - which is what\nmakes it a spend rather than a write.\n\n409 when a plan already exists: this only creates a FIRST version. Replan\nan existing one with `POST .../plan` (caller-authored, free) or from a\nreview card with `POST /desk/decisions/{id}/replan` (charged).\n422 when the company has no contacts to plan around yet.","operationId":"draft_account_plan_desk_accounts__account_id__plan_draft_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"The account's mashup company id (`cb_account_plans.account_id`).","title":"Account Id"},"description":"The account's mashup company id (`cb_account_plans.account_id`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AccountPlanPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/desk/accounts/{account_id}/plan/steps/{step_id}":{"put":{"tags":["Desk"],"summary":"Update Account Plan Step","description":"Approve, reject or edit ONE step on the latest plan version.\n\nThe only in-place edit on this surface. Approving a step does not SEND it -\nit marks it ready, and the desk raises it as a card when its time comes.","operationId":"update_account_plan_step_desk_accounts__account_id__plan_steps__step_id__put","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"The account's mashup company id (`cb_account_plans.account_id`).","title":"Account Id"},"description":"The account's mashup company id (`cb_account_plans.account_id`)."},{"name":"step_id","in":"path","required":true,"schema":{"type":"string","description":"Step id, as carried on the plan.","title":"Step Id"},"description":"Step id, as carried on the plan."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AccountPlanStepUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AccountPlanPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/desk/accounts/{account_id}/plan/preview":{"post":{"tags":["Desk"],"summary":"Preview Account Plan","description":"Diff a proposed plan against the current version. WRITES NOTHING.\n\nPOST only because the proposed plan is a body. It persists nothing, spends\nnothing and does not consume the signal-replanner cooldown, so it is tiered\na READ - a read-only key must be able to see what an apply would change\nbefore anyone applies it.","operationId":"preview_account_plan_desk_accounts__account_id__plan_preview_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"The account's mashup company id (`cb_account_plans.account_id`).","title":"Account Id"},"description":"The account's mashup company id (`cb_account_plans.account_id`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AccountPlanPreviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AccountPlanPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/accounts/{account_id}/plan/apply":{"post":{"tags":["Desk"],"summary":"Apply Account Plan","description":"Persist the approved steps as a NEW plan version, and return the diff.\n\n`proposed_plan` must be non-empty. Apply REPLACES the account's steps, so\nan empty proposal would blank an active plan; the app answers 400 rather\nthan doing it. Prior versions stay immutable and readable.","operationId":"apply_account_plan_desk_accounts__account_id__plan_apply_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"The account's mashup company id (`cb_account_plans.account_id`).","title":"Account Id"},"description":"The account's mashup company id (`cb_account_plans.account_id`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AccountPlanApplyRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AccountPlanPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/desk/accounts/{account_id}/context":{"get":{"tags":["Desk"],"summary":"Get Account Context","description":"Why this account is here: summary, timeline, deal state, committee.\n\nRead-only; never writes. This is the evidence a plan is built from, so it\nis the right read before proposing one.","operationId":"get_account_context_desk_accounts__account_id__context_get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"The account's mashup company id (`cb_account_plans.account_id`).","title":"Account Id"},"description":"The account's mashup company id (`cb_account_plans.account_id`)."},{"name":"activity_limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Activity Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AccountPlanPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/accounts/{account_id}/committee":{"post":{"tags":["Desk"],"summary":"Edit Account Committee","description":"Add and remove buying-committee members.\n\nRides plan versioning like everything else: it persists a NEW plan version\npreserving the existing steps, rather than mutating the committee in place.\nBoth lists apply in the same version, so the committee is never left\nhalf-changed.","operationId":"edit_account_committee_desk_accounts__account_id__committee_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"The account's mashup company id (`cb_account_plans.account_id`).","title":"Account Id"},"description":"The account's mashup company id (`cb_account_plans.account_id`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CommitteeEditRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AccountPlanPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/desk/accounts/{account_id}/committee/plays":{"get":{"tags":["Desk"],"summary":"List Committee Plays","description":"Workflows that can be fired at this account's committee.\n\nOnly the ones the desk would actually run - the listing applies the same\nfilter the run does. Read-only; runs nothing.","operationId":"list_committee_plays_desk_accounts__account_id__committee_plays_get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"The account's mashup company id (`cb_account_plans.account_id`).","title":"Account Id"},"description":"The account's mashup company id (`cb_account_plans.account_id`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AccountPlanListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/accounts/{account_id}/committee/plays/{action_id}/check":{"get":{"tags":["Desk"],"summary":"Check Committee Play","description":"What running this workflow at this committee would DO, in plain words.\n\nIts effects, who it would run for, who it already ran for, and whether the\ndesk refuses it. Read-only; runs nothing and spends nothing. This is the\ncall to make before the run below.","operationId":"check_committee_play_desk_accounts__account_id__committee_plays__action_id__check_get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"The account's mashup company id (`cb_account_plans.account_id`).","title":"Account Id"},"description":"The account's mashup company id (`cb_account_plans.account_id`)."},{"name":"action_id","in":"path","required":true,"schema":{"type":"string","description":"Play id, from `.../committee/plays`.","title":"Action Id"},"description":"Play id, from `.../committee/plays`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AccountPlanPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/desk/accounts/{account_id}/committee/plays/{action_id}/run":{"post":{"tags":["Desk"],"summary":"Run Committee Play","description":"Fire one workflow at EVERY REACHABLE COMMITTEE MEMBER. One run each.\n\nThis is the fan-out on this surface, and it is why the operation is not a\nplain write: one call becomes one workflow execution per person, and a\nworkflow can email or message. Read `.../check` first - it names exactly\nwho this would reach.\n\nIDEMPOTENT per (org, account, play, member) for one hour, so a retried\npress does not double up on anyone. 409 is a refusal with nothing fired,\nnot a failure.","operationId":"run_committee_play_desk_accounts__account_id__committee_plays__action_id__run_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"The account's mashup company id (`cb_account_plans.account_id`).","title":"Account Id"},"description":"The account's mashup company id (`cb_account_plans.account_id`)."},{"name":"action_id","in":"path","required":true,"schema":{"type":"string","description":"Play id, from `.../committee/plays`.","title":"Action Id"},"description":"Play id, from `.../committee/plays`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AccountPlanPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/desk/accounts/{account_id}/committee/{contact_id}/find-linkedin":{"post":{"tags":["Desk"],"summary":"Find Committee Member Linkedin","description":"SPENDS CREDITS. Find ONE committee member's LinkedIn profile.\n\nAbout five credits per attempt, CHARGED ON A MISS AS WELL AS A HIT - both\nproviders in the pipeline bill on no-match, at a measured 58% hit rate. So\nthe cost is per call, not per result.\n\nDeliberately ONE contact per call, and the contact must be on THIS\naccount's committee. There is no bulk entry point and this surface does not\nadd one: pointed at contacts generally it would be a seven-figure credit\nbutton.\n\nQueues an ASYNC lookup - the result lands on the contact record afterwards,\nso read it back from `/desk/committee-targets`.","operationId":"find_committee_member_linkedin_desk_accounts__account_id__committee__contact_id__find_linkedin_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"The account's mashup company id (`cb_account_plans.account_id`).","title":"Account Id"},"description":"The account's mashup company id (`cb_account_plans.account_id`)."},{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"The committee member to look up.","title":"Contact Id"},"description":"The committee member to look up."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AccountPlanPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/desk/accounts/{account_id}/committee/{contact_id}/linkedin-invite":{"post":{"tags":["Desk"],"summary":"Send Committee Linkedin Invite","description":"REACHES A REAL PERSON on LinkedIn, from the rep's own account.\n\nCosts no credits, and that is not the point: a connection request arrives\nin someone's notifications under a named human's identity and CANNOT BE\nWITHDRAWN. That is why it is tiered alongside the sends rather than with\nthe writes.\n\nThe sender is the rep's OWN claimed LinkedIn account, resolved strictly -\nit fails closed rather than falling back to whichever account the org\nconnected first. Claim one with `PUT /desk/linkedin-sender`.\n\n409 on every refusal, with nothing queued: no sender picked, the account is\nnot connected, the person is not on this committee, or an invite is already\nqueued for them.","operationId":"send_committee_linkedin_invite_desk_accounts__account_id__committee__contact_id__linkedin_invite_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"The account's mashup company id (`cb_account_plans.account_id`).","title":"Account Id"},"description":"The account's mashup company id (`cb_account_plans.account_id`)."},{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"The committee member to invite.","title":"Contact Id"},"description":"The committee member to invite."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CommitteeLinkedInInviteRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AccountPlanPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/deals/pipelines":{"get":{"tags":["Deals"],"summary":"List Pipelines","description":"List all deal pipelines and their stages.","operationId":"list_pipelines_deals_pipelines_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_PipelineResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/deals":{"get":{"tags":["Deals"],"summary":"List Deals","description":"List all deals org-wide with optional filters and pagination.","operationId":"list_deals_deals_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number","default":1,"title":"Page"},"description":"Page number"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page","default":50,"title":"Limit"},"description":"Items per page"},{"name":"stage_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by stage ID","title":"Stage Id"},"description":"Filter by stage ID"},{"name":"pipeline_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by pipeline ID","title":"Pipeline Id"},"description":"Filter by pipeline ID"},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Search by deal name","title":"Search"},"description":"Search by deal name"},{"name":"owner_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by owner ID","title":"Owner Id"},"description":"Filter by owner ID"},{"name":"owner_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by owner email","title":"Owner Email"},"description":"Filter by owner email"},{"name":"outcome","in":"query","required":false,"schema":{"anyOf":[{"enum":["won","lost","open"],"type":"string"},{"type":"null"}],"description":"Filter by deal outcome. A deal is won, lost, or open - exactly one. Prefer this over is_closed_won: the boolean's false branch means 'not won', which returns open AND unclassified deals alongside lost ones, and is the wrong cohort for closed-lost re-engagement.","title":"Outcome"},"description":"Filter by deal outcome. A deal is won, lost, or open - exactly one. Prefer this over is_closed_won: the boolean's false branch means 'not won', which returns open AND unclassified deals alongside lost ones, and is the wrong cohort for closed-lost re-engagement."},{"name":"is_closed_won","in":"query","required":false,"schema":{"anyOf":[{"type":"boolean"},{"type":"null"}],"description":"LEGACY - prefer outcome=. Retained for backwards compatibility with existing consumers. true means won; false means NOT won (open, lost and unclassified deals), which is rarely what a caller intends.","title":"Is Closed Won"},"description":"LEGACY - prefer outcome=. Retained for backwards compatibility with existing consumers. true means won; false means NOT won (open, lost and unclassified deals), which is rarely what a caller intends."},{"name":"last_activity_before","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"description":"Only deals last touched before this timestamp","title":"Last Activity Before"},"description":"Only deals last touched before this timestamp"},{"name":"stale_before","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"description":"Deals last touched before this timestamp OR never touched at all. Union of last_activity_before and the no-activity cohort - use this for 'my stale deals' (last_activity_before alone excludes deals with no recorded activity, since NULL is never earlier-than).","title":"Stale Before"},"description":"Deals last touched before this timestamp OR never touched at all. Union of last_activity_before and the no-activity cohort - use this for 'my stale deals' (last_activity_before alone excludes deals with no recorded activity, since NULL is never earlier-than)."},{"name":"has_activity","in":"query","required":false,"schema":{"anyOf":[{"type":"boolean"},{"type":"null"}],"description":"Filter by whether the deal has recorded activity","title":"Has Activity"},"description":"Filter by whether the deal has recorded activity"},{"name":"has_contact","in":"query","required":false,"schema":{"anyOf":[{"type":"boolean"},{"type":"null"}],"description":"Filter by whether the deal has a route to any contact. false returns the orphaned-deal cohort: no cb_deal_contacts row AND no live primary contact (a primary_contact_id pointing at a soft-deleted or merged-away contact counts as no route). Same definition the Data Quality panel counts, so the two can never disagree.","title":"Has Contact"},"description":"Filter by whether the deal has a route to any contact. false returns the orphaned-deal cohort: no cb_deal_contacts row AND no live primary contact (a primary_contact_id pointing at a soft-deleted or merged-away contact counts as no route). Same definition the Data Quality panel counts, so the two can never disagree."},{"name":"close_after","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"description":"Only deals whose close_date is on/after this timestamp (inclusive lower bound). Pair with close_before for a period window, and with outcome=won for 'deals we closed-won in this period'. A period count needs BOTH a lower bound and the outcome join: close_before alone sums the entire deal history into every period. Deals with a NULL close_date are excluded (a deal with no close date is not closing in any window). A naive timestamp is treated as UTC.","title":"Close After"},"description":"Only deals whose close_date is on/after this timestamp (inclusive lower bound). Pair with close_before for a period window, and with outcome=won for 'deals we closed-won in this period'. A period count needs BOTH a lower bound and the outcome join: close_before alone sums the entire deal history into every period. Deals with a NULL close_date are excluded (a deal with no close date is not closing in any window). A naive timestamp is treated as UTC."},{"name":"close_before","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"description":"Only deals whose close_date is strictly before this timestamp (exclusive upper bound). The window is half-open [close_after, close_before) so adjacent periods never double-count a deal that closes exactly on a boundary. A naive timestamp is treated as UTC (the close_date column is timestamp without time zone).","title":"Close Before"},"description":"Only deals whose close_date is strictly before this timestamp (exclusive upper bound). The window is half-open [close_after, close_before) so adjacent periods never double-count a deal that closes exactly on a boundary. A naive timestamp is treated as UTC (the close_date column is timestamp without time zone)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_DealResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"post":{"tags":["Deals"],"summary":"Create Deal","description":"Create a new deal. Defaults to the org's default pipeline and first stage if not specified.\n\n``background_tasks`` carries the ``deal.created`` event only (#16242). Like\nthe PATCH endpoint's stage fan-out it is injected, not a body field, so it\ndoes not appear in the OpenAPI schema and the request contract is unchanged.\nQueuing it there rather than publishing inline keeps the Redis round trip\noff the caller's latency budget and makes \"strictly after the commit\"\nstructural: the task is queued only once the session context has exited,\nand FastAPI attaches background tasks to the SUCCESS response, so a raise\nanywhere above publishes nothing.","operationId":"create_deal_deals_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DealCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/deals/{deal_id}":{"get":{"tags":["Deals"],"summary":"Get Deal","description":"Get a single deal by ID.","operationId":"get_deal_deals__deal_id__get","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal ID (UUID)","title":"Deal Id"},"description":"Deal ID (UUID)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Deals"],"summary":"Update Deal","description":"Update a deal (partial update).\n\nContact operations run in a fixed order within the single transaction:\n``remove_contact_ids`` -> ``add_contact_ids`` -> ``contact_roles``. That\norder is what makes the useful combinations work:\n\n* a contact linked by ``add_contact_ids`` in THIS request can be given a\n  role by ``contact_roles`` in the same call (roles run last);\n* an id in both ``remove_contact_ids`` and ``add_contact_ids`` ends up\n  linked (add runs after remove), so a role for it still applies;\n* an id in ``remove_contact_ids`` and ``contact_roles`` but NOT in\n  ``add_contact_ids`` is unlinked by the time roles run, so it is a 422\n  naming that id rather than a role written to a row that no longer\n  exists.\n\nA ``contact_roles`` entry for a contact that is neither already linked nor\nbeing added is a 422; the whole transaction rolls back, so a partially\napplied batch is not a state this endpoint can produce.\n\n``background_tasks`` carries the ``deal.stage_changed`` fan-out only. It is\ninjected, not a body field, so it does not appear in the OpenAPI schema and\nthe request contract is unchanged (pinned by\n``developer_api/tests/test_deal_stage_events.py``). Publishing there rather\nthan inline keeps the Redis round trip off the caller's latency budget and\nmakes \"strictly after the commit\" structural: the task is queued only after\nthe session context has exited, and FastAPI attaches background tasks to the\nSUCCESS response, so a raise anywhere above publishes nothing.","operationId":"update_deal_deals__deal_id__patch","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal ID (UUID)","title":"Deal Id"},"description":"Deal ID (UUID)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DealUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Deals"],"summary":"Delete Deal","description":"Delete a deal.\n\nTHE TOMBSTONE RULE (#16242): ``deal.deleted`` has to be self-contained,\nbecause by the time a consumer reads it the row is gone and ``deal_id``\nresolves to nothing. The payload therefore comes from ``RETURNING`` on the\nDELETE itself — one round trip, and no window in which a concurrent write\ncould change what a preceding SELECT had read. ``background_tasks`` is\ninjected (not a body field, so the OpenAPI schema is unchanged) for the\nsame reason as on PATCH.","operationId":"delete_deal_deals__deal_id__delete","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal ID (UUID)","title":"Deal Id"},"description":"Deal ID (UUID)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"deals:delete","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/contacts/{contact_id}":{"put":{"tags":["Deals"],"summary":"Set Deal Contact Role","description":"Set (or clear) a contact's buying-committee role on a deal.\n\nThe role lives on the deal-contact LINK (`cb_deal_contacts.role`), not on\nthe contact: the same person can be a champion on one deal and an end user\non another. This endpoint only re-roles an EXISTING link — it never\ncreates one, so attaching and roling stay separately auditable. Use\n``PATCH /deals/{deal_id}`` with ``add_contact_ids`` (optionally alongside\n``contact_roles``) to link a contact first.\n\n``{contact_id}`` is the ``mashup_contact_id``, the same integer id this API\nuses for a contact everywhere else (``GET /contacts/{id}``, the ``id`` on\nevery ``ContactBrief``). The internal app route calls the identical value\n``{person_id}``; that name is a historical misnomer and is not repeated\nhere.\n\nBody is ``{\"role\": \"champion\"}``; an explicit ``{\"role\": null}`` clears the\nrole. ``role`` is required — an empty body is a 422, because a PUT that\nnames no new state for the sub-resource is a caller bug, and reading\nomission as \"clear\" would destroy data on a typo.\n\nReturns the updated contact. 404 when the deal does not exist in this org\nor the contact is not linked to it; 422 on a role outside the vocabulary.","operationId":"set_deal_contact_role_deals__deal_id__contacts__contact_id__put","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal ID (UUID)","title":"Deal Id"},"description":"Deal ID (UUID)"},{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"mashup_contact_id (BigInt) of a contact already linked to this deal","title":"Contact Id"},"description":"mashup_contact_id (BigInt) of a contact already linked to this deal"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DealContactRoleUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContactBrief_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/deals":{"get":{"tags":["Deals"],"summary":"Get Contact Deals","description":"Get all deals associated with a contact.","operationId":"get_contact_deals_contacts__contact_id__deals_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact ID","title":"Contact Id"},"description":"Contact ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_ContactDealResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/deals":{"get":{"tags":["Deals"],"summary":"Get Company Deals","description":"Get all deals associated with a company.","operationId":"get_company_deals_companies__company_id__deals_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"Company ID","title":"Company Id"},"description":"Company ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_ContactDealResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/lifecycle-stages":{"get":{"tags":["Revenue Lifecycle"],"summary":"List Lifecycle Stages","description":"List the org's configured revenue lifecycle stages, sorted for display.\n\nSuspects/Leads/Trial/Customers/Churned ship seeded by default; an org may\nalso have added custom stages via the Settings > Revenue Lifecycle editor.\nPass either `slug` or `id` from this response to\n`GET /lifecycle-stages/{stage}/records` and\n`POST /{companies,contacts}/{id}/lifecycle-stage`.","operationId":"list_lifecycle_stages_lifecycle_stages_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_LifecycleStageResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/lifecycle-stages/counts":{"get":{"tags":["Revenue Lifecycle"],"summary":"Get Lifecycle Stage Counts","description":"Per-stage company counts — cheap enough to power a lifecycle board header.\n\nThe returned map is keyed by lifecycle ENTRY ID, not slug (matches\n`GET /settings/revenue/lifecycle/counts` exactly — see\n`.claude/agent-context/lifecycle-stage-moves.md` Gotcha 4). Cross-reference\nagainst `GET /lifecycle-stages` to resolve an id to its slug/name. Counts\nare company-only, same as the app's nav badges — contact-stage membership\nhas no counts surface yet (see the module docstring's dropped-scope note).","operationId":"get_lifecycle_stage_counts_lifecycle_stages_counts_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__int__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/lifecycle-stages/{stage}/records":{"get":{"tags":["Revenue Lifecycle"],"summary":"List Lifecycle Stage Records","description":"List the companies currently in a lifecycle stage.\n\nMembership is resolved with the exact same predicate the Suspects/Leads/\nTrial/Customers/Churned grid and the counts endpoint use — this endpoint,\nthe grid, and `GET /lifecycle-stages/counts` can never disagree about who\nis in a stage. Row visibility is additionally narrowed by the calling\nkey's declared company scope (own/team/all), same as `GET /companies`.","operationId":"list_lifecycle_stage_records_lifecycle_stages__stage__records_get","parameters":[{"name":"stage","in":"path","required":true,"schema":{"type":"string","description":"Lifecycle slug (e.g. 'leads') OR lifecycle entry UUID — either works.","title":"Stage"},"description":"Lifecycle slug (e.g. 'leads') OR lifecycle entry UUID — either works."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (1-indexed).","default":1,"title":"Page"},"description":"Page number (1-indexed)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page (max 200).","default":50,"title":"Limit"},"description":"Items per page (max 200)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_LifecycleRecordItem__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/lifecycle-stage":{"post":{"tags":["Revenue Lifecycle"],"summary":"Move Company Lifecycle Stage","description":"Move a company to a different lifecycle stage.\n\nProxies `promote_company_lifecycle_stage` — atomically writes `status` +\n`custom_status` to both the `cb_accounts` and `cb_company_extensions`\noverlays, refuses a move to `customers` when the company has no active/\npast_due Stripe subscription (400, same guard the app enforces), and\nrecords a `cb_lead_stage_history`-style audit row. `org_id` is always the\nauthenticated key's own organisation; there is no way to target another\norg's company through this endpoint.\n\nA move to `churned` (or any stage that writes status 'churned') is refused\nwith a 400 unless the company is or was a customer. `target_slug` ignores\ncase and surrounding whitespace. `dry_run: true` runs every check and\nreturns the would-be transition without writing anything.\n\nA move to `customers` of a company with no subscription at all is a 409\n(`detail.code` 'customers_without_subscription', `detail.message` names the\ncompany) unless `confirm_without_subscription: true` is sent (R3-30).","operationId":"move_company_lifecycle_stage_companies__company_id__lifecycle_stage_post","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"Company ID (mashup_companies.id, same as GET /companies/{company_id}).","title":"Company Id"},"description":"Company ID (mashup_companies.id, same as GET /companies/{company_id})."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LifecycleStageMoveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LifecycleStageMoveResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/lifecycle-stage":{"post":{"tags":["Revenue Lifecycle"],"summary":"Move Contact Lifecycle Stage","description":"Move a contact to a different lifecycle stage.\n\nProxies `promote_contact_lifecycle_stage` — writes `cb_contact_extensions\n.custom_status` (auto-creating the extension row if the contact has none\nyet, which is common for Suspects-stage contacts), and records the same\naudit trail the in-app Move-Stage dialog's contact mode does. Returns no\ncontact PII (see the module docstring) — only the status transition.\n\nA move to `customers` of a contact with no company, or whose company has no\nsubscription, is a 409 (`detail.code` 'customers_without_subscription')\nunless `confirm_without_subscription: true` is sent (R3-31).","operationId":"move_contact_lifecycle_stage_contacts__contact_id__lifecycle_stage_post","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact ID — accepts mashup_contacts.CONTACT_ID or .id, same as GET /contacts/{contact_id}.","title":"Contact Id"},"description":"Contact ID — accepts mashup_contacts.CONTACT_ID or .id, same as GET /contacts/{contact_id}."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LifecycleStageMoveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LifecycleStageMoveResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/lifecycle/column-fill-rates":{"get":{"tags":["Revenue Lifecycle"],"summary":"Get Lifecycle Column Fill Rates","description":"Share of a stage's records that have a value in each optional column (cached for an hour).\n\nRead-only and aggregate: percentages per column over the organisation's records, never a record or an identity,\nlike `GET /lifecycle-stages/counts`. Computed in the key's own organisation under a statement timeout.","operationId":"get_lifecycle_column_fill_rates_lifecycle_column_fill_rates_get","parameters":[{"name":"view","in":"query","required":false,"schema":{"enum":["companies","contacts"],"type":"string","description":"Which grid: the stage's companies or its contacts.","default":"companies","title":"View"},"description":"Which grid: the stage's companies or its contacts."},{"name":"lifecycle_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":128},{"type":"null"}],"description":"Lifecycle entry id; omit for all stages.","title":"Lifecycle Id"},"description":"Lifecycle entry id; omit for all stages."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ColumnFillRatesResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/quotes":{"get":{"tags":["Quotes"],"summary":"List Quotes","description":"List quotes for the org with optional status / company / deal / owner filters.","operationId":"list_quotes_quotes_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by quote status: draft, sent, viewed, accepted, declined, voided, expired, archived","title":"Status"},"description":"Filter by quote status: draft, sent, viewed, accepted, declined, voided, expired, archived"},{"name":"include_archived","in":"query","required":false,"schema":{"type":"boolean","description":"Also return archived quotes when no status is given","default":false,"title":"Include Archived"},"description":"Also return archived quotes when no status is given"},{"name":"mashup_company_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Filter quotes for a specific company","title":"Mashup Company Id"},"description":"Filter quotes for a specific company"},{"name":"deal_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter quotes linked to a specific deal (UUID)","title":"Deal Id"},"description":"Filter quotes linked to a specific deal (UUID)"},{"name":"owner_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter quotes owned by a specific user (email)","title":"Owner Id"},"description":"Filter quotes owned by a specific user (email)"},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuoteListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"},"post":{"tags":["Quotes"],"summary":"Create Quote","description":"Create a new quote in `draft` status. Always creates — never sends.","operationId":"create_quote_quotes_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuoteDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}":{"get":{"tags":["Quotes"],"summary":"Get Quote","description":"Get full quote detail: line items, activity log, envelope tracking, resolved contact/company names.","operationId":"get_quote_quotes__quote_id__get","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Quote UUID","title":"Quote Id"},"description":"Quote UUID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuoteDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Quotes"],"summary":"Update Quote","description":"Update a quote in place (``PUT`` or ``PATCH`` — both accepted).\n\nAll fields are optional; only the ones you send change. Draft quotes edit\ndirectly. A ``sent`` / ``viewed`` quote is recalled to draft first (voiding\nits live signing link) while keeping the same row + quote number; terminal\nquotes (accepted/declined/voided/expired) reject the update.\n\n``owner_id`` reassigns the quote's AE (a blank value is ignored — it never\nnulls an existing owner). ``billing_legal_name`` / ``billing_email`` /\n``billing_primary_email`` / ``billing_address`` set the customer's billing\nidentity. Passing ``line_items`` replaces the entire line-item set (and\nre-runs quotable-product authorization). Totals recalculate automatically.","operationId":"update_quote_quotes__quote_id__patch","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Quote UUID","title":"Quote Id"},"description":"Quote UUID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuoteDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"},"put":{"tags":["Quotes"],"summary":"Update Quote","description":"Update a quote in place (``PUT`` or ``PATCH`` — both accepted).\n\nAll fields are optional; only the ones you send change. Draft quotes edit\ndirectly. A ``sent`` / ``viewed`` quote is recalled to draft first (voiding\nits live signing link) while keeping the same row + quote number; terminal\nquotes (accepted/declined/voided/expired) reject the update.\n\n``owner_id`` reassigns the quote's AE (a blank value is ignored — it never\nnulls an existing owner). ``billing_legal_name`` / ``billing_email`` /\n``billing_primary_email`` / ``billing_address`` set the customer's billing\nidentity. Passing ``line_items`` replaces the entire line-item set (and\nre-runs quotable-product authorization). Totals recalculate automatically.","operationId":"update_quote_quotes__quote_id__put","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Quote UUID","title":"Quote Id"},"description":"Quote UUID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuoteDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Quotes"],"summary":"Delete Quote","description":"Delete a draft quote. 400s on any non-draft status (legal-record preservation).","operationId":"delete_quote_quotes__quote_id__delete","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Quote UUID","title":"Quote Id"},"description":"Quote UUID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"quotes:delete","x-graph8-lifecycle":"active"}},"/quotable-products":{"get":{"tags":["Quotes"],"summary":"List Quotable Products","description":"List products available for quote line items (Stripe catalog + org manual catalog).","operationId":"list_quotable_products_quotable_products_get","parameters":[{"name":"currency","in":"query","required":false,"schema":{"anyOf":[{"type":"string","minLength":3,"maxLength":3},{"type":"null"}],"description":"Filter prices to this currency code (e.g. USD)","title":"Currency"},"description":"Filter prices to this currency code (e.g. USD)"},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotableProductsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/quote-settings":{"get":{"tags":["Quotes"],"summary":"Get Quote Settings","description":"Get org quote settings (branding, default terms, sender identity).\n\nAuto-creates default settings if none exist for the org.","operationId":"get_quote_settings_quote_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuoteSettingsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"},"put":{"tags":["Quotes"],"summary":"Update Quote Settings","description":"Org-wide quote branding, terms and sender identity. ORG ADMIN.\n\n`GET /quote-settings` was already published; this is its write half. Admin\nbecause `sender_email` decides whose name every quote goes out under.","operationId":"update_quote_settings_quote_settings_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteSettingsUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/companies/{company_id}/quotes":{"get":{"tags":["Quotes"],"summary":"Get Company Quotes","description":"List every quote attached to a given company (account view).","operationId":"get_company_quotes_companies__company_id__quotes_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"MashupCompany ID","title":"Company Id"},"description":"MashupCompany ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_QuoteDetail__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/quotes":{"get":{"tags":["Quotes"],"summary":"Get Contact Quotes","description":"List quotes where this contact is the signer.","operationId":"get_contact_quotes_contacts__contact_id__quotes_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"MashupContact ID (the quote signer)","title":"Contact Id"},"description":"MashupContact ID (the quote signer)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_QuoteDetail__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}/duplicate":{"post":{"tags":["Quotes"],"summary":"Duplicate Quote","description":"Clone any quote into a new draft. The copy keeps the source title; its new quote number tells them apart.","operationId":"duplicate_quote_quotes__quote_id__duplicate_post","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Source quote UUID (any status)","title":"Quote Id"},"description":"Source quote UUID (any status)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuoteDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}/edit-as-draft":{"post":{"tags":["Quotes"],"summary":"Edit Quote As Draft","description":"Convert a sent quote back into an editable draft via void+clone.\n\nVoids the existing signing envelope (so the recipient's link stops\nresolving), marks the source ``voided``, and creates a fresh ``draft``\nwith all the line items copied across. Returns\n``{new_quote_id, new_quote_number, voided_envelope_id, source_quote_id}``.\nThe caller should navigate to / update the new draft.","operationId":"edit_quote_as_draft_quotes__quote_id__edit_as_draft_post","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Source quote UUID (must be in 'sent' status)","title":"Quote Id"},"description":"Source quote UUID (must be in 'sent' status)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}/send":{"post":{"tags":["Quotes"],"summary":"Send Quote","description":"Send the quote for e-signature (or resend if it's already in flight).\n\nSide effects: creates / reuses a signing envelope, sends the\ncustomer-facing email via SES, logs to the universal inbox, rolls\nquote status forward to ``sent``. Recipient is resolved from\n``signer_contact_id`` or ``signer_email`` (one must be set).\n\nIdempotent for resend: when the quote already has an envelope in\n``sent`` or ``viewed`` state, the existing envelope is re-emailed\nand the recipient keeps the original signing link.\n\nRefused with 400 ``QUOTE_ZERO_TOTAL`` for a $0 quote and\n``QUOTE_TAX_EXCEEDS_TAXABLE`` when tax is larger than the amount it\ntaxes (subtotal less discounts). Nothing is sent; fix the quote first.","operationId":"send_quote_quotes__quote_id__send_post","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Quote UUID (must be in draft or sent status)","title":"Quote Id"},"description":"Quote UUID (must be in draft or sent status)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteSendRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuoteDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}/archive":{"post":{"tags":["Quotes"],"summary":"Archive Quote","description":"Take a quote off the active list. REVERSIBLE - see `/unarchive`.","operationId":"archive_quote_quotes__quote_id__archive_post","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Quote id (UUID).","title":"Quote Id"},"description":"Quote id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"quotes:delete","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}/unarchive":{"post":{"tags":["Quotes"],"summary":"Unarchive Quote","description":"Restore an archived quote to the active list.\n\nA quote that is not archived comes back unchanged - unarchiving an already\nactive quote is a no-op and announces nothing. Stated because the sibling\nsequence unarchive raises 403 unconditionally and had to be withdrawn from\nthe contract; this one is genuinely callable.","operationId":"unarchive_quote_quotes__quote_id__unarchive_post","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Quote id (UUID).","title":"Quote Id"},"description":"Quote id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}/expire":{"post":{"tags":["Quotes"],"summary":"Expire Quote","description":"Mark a quote expired. TERMINAL - the customer's link stops working.","operationId":"expire_quote_quotes__quote_id__expire_post","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Quote id (UUID).","title":"Quote Id"},"description":"Quote id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"quotes:delete","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}/revoke":{"post":{"tags":["Quotes"],"summary":"Revoke Quote","description":"Withdraw a quote the customer has already been sent. TERMINAL.\n\nRevoke rather than expire when the offer itself was wrong: it pulls the\ndocument back rather than letting it lapse.","operationId":"revoke_quote_quotes__quote_id__revoke_post","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Quote id (UUID).","title":"Quote Id"},"description":"Quote id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"quotes:delete","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}/mark-accepted":{"post":{"tags":["Quotes"],"summary":"Mark Quote Accepted","description":"Accept a quote on the customer's behalf. THIS RAISES AN INVOICE.\n\nIt runs the same provisioning path a signed envelope runs: the quote flips\nto accepted, the total rolls up to the linked deal, and\n`provision_from_accepted_quote` materialises the invoice or subscription\nwith the org's configured billing provider. Use it when the customer paid\nor signed outside graph8, not to tidy up a stale quote.\n\n`evidence_type` and `evidence_note` are REQUIRED and land on the audit row\nstamped `method=\"manual\"`, so a manual accept stays distinguishable from a\nsigned-envelope accept forever.\n\nThe app additionally requires the caller to be an Owner/Admin or the\nresolved quote/deal owner, and refuses a quote that is not in the\nsent/viewed transition set with a 409.","operationId":"mark_quote_accepted_quotes__quote_id__mark_accepted_post","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Quote id (UUID).","title":"Quote Id"},"description":"Quote id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ManualAcceptRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}/pdf":{"get":{"tags":["Quotes"],"summary":"Get Quote Pdf","description":"The quote document, as the customer sees it.","operationId":"get_quote_pdf_quotes__quote_id__pdf_get","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Quote id (UUID).","title":"Quote Id"},"description":"Quote id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}/send-preview":{"post":{"tags":["Quotes"],"summary":"Preview Quote Send","description":"Render the exact email and document `/send` would produce. SENDS NOTHING.\n\nTakes the identical body to `/send` on purpose - a preview rendered from a\ndifferent body predicts nothing. `deliver` is accepted and inert.\n\nTiered as a READ: it renders and returns, and nothing in the handler\nreaches a mail transport.","operationId":"preview_quote_send_quotes__quote_id__send_preview_post","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Quote id (UUID).","title":"Quote Id"},"description":"Quote id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteSendPreviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/quotes/preview-draft":{"post":{"tags":["Quotes"],"summary":"Preview Quote Draft","description":"Render a quote that does not exist yet. Creates nothing.","operationId":"preview_quote_draft_quotes_preview_draft_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"A draft quote, in the same shape `POST /quotes` takes. Passed through open rather than mirrored: this renders whatever it is given and stores nothing, so a field this contract had not caught up with would be dropped from the PREVIEW while the real quote kept it - a preview that lies about the document.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/quotes/payment-schedule":{"post":{"tags":["Quotes"],"summary":"Preview Payment Schedule","description":"What a set of line items would bill, and when. Arithmetic over the body.","operationId":"preview_payment_schedule_quotes_payment_schedule_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PaymentSchedulePreviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/quotes/batch":{"post":{"tags":["Quotes"],"summary":"Batch Quote Action","description":"Archive, expire or revoke up to 200 quotes.\n\nREAD THE PER-ROW RESULT, not the HTTP status. Each quote runs in its own\ntransaction, so a 200 here means \"the batch ran\", not \"every quote moved\":\nan out-of-scope id comes back `forbidden`, an unknown one `error`, and a\nquote whose status makes the action meaningless comes back `skipped`.","operationId":"batch_quote_action_quotes_batch_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BatchQuoteActionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuoteListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/quote-templates":{"get":{"tags":["Quotes"],"summary":"List Quote Templates","description":"Reusable quote templates. A READ - any key, not just an admin's.\n\nMatching the app, where listing is `get_current_user` and only the writes\nbelow are admin-gated.","operationId":"list_quote_templates_quote_templates_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuoteListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"},"post":{"tags":["Quotes"],"summary":"Create Quote Template","description":"Create a template. ORG ADMIN - it changes what every future quote starts as.","operationId":"create_quote_template_quote_templates_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteTemplateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/quote-templates/{template_id}":{"put":{"tags":["Quotes"],"summary":"Update Quote Template","description":"Replace a template. ORG ADMIN.\n\nA PUT, matching the app: the body is the template's new state, not a patch,\nso an omitted field is CLEARED rather than left alone.","operationId":"update_quote_template_quote_templates__template_id__put","parameters":[{"name":"template_id","in":"path","required":true,"schema":{"type":"string","description":"Template id.","title":"Template Id"},"description":"Template id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteTemplateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Quotes"],"summary":"Delete Quote Template","description":"Delete a template. ORG ADMIN. Quotes already built from it are untouched.","operationId":"delete_quote_template_quote_templates__template_id__delete","parameters":[{"name":"template_id","in":"path","required":true,"schema":{"type":"string","description":"Template id.","title":"Template Id"},"description":"Template id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"quotes:delete","x-graph8-lifecycle":"active"}},"/quote-settings/documents":{"get":{"tags":["Quotes"],"summary":"List Quote Documents","description":"The reusable legal documents a template can attach. A READ.","operationId":"list_quote_documents_quote_settings_documents_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuoteListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"},"post":{"tags":["Quotes"],"summary":"Upload Quote Document","description":"Upload a legal document to the org's library. ORG ADMIN.\n\nMultipart, like the app. The PDF-only and 10 MB rules are the app's and are\nenforced there; they are documented here so a caller sees them before\nspending the upload.","operationId":"upload_quote_document_quote_settings_documents_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_quote_document_quote_settings_documents_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/quote-settings/documents/{doc_id}":{"delete":{"tags":["Quotes"],"summary":"Delete Quote Document","description":"Remove a document from the library. ORG ADMIN.","operationId":"delete_quote_document_quote_settings_documents__doc_id__delete","parameters":[{"name":"doc_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Doc Id"},"description":"Document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"quotes:delete","x-graph8-lifecycle":"active"}},"/quote-contacts":{"get":{"tags":["Quotes"],"summary":"Search Quote Contacts","description":"Find a contact to put on a quote as signer or billing contact.","operationId":"search_quote_contacts_quote_contacts_get","parameters":[{"name":"q","in":"query","required":false,"schema":{"type":"string","maxLength":200,"description":"Name or email fragment. Empty returns the default page.","default":"","title":"Q"},"description":"Name or email fragment. Empty returns the default page."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"description":"The app's default is 100 and deliberately not smaller: the signer picker has to show every plausible match, and a short page reads as 'this contact does not exist'.","default":100,"title":"Limit"},"description":"The app's default is 100 and deliberately not smaller: the signer picker has to show every plausible match, and a short page reads as 'this contact does not exist'."},{"name":"company_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Scope to contacts at this company.","title":"Company Id"},"description":"Scope to contacts at this company."},{"name":"deal_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Scope to contacts linked to this deal. Combined with `company_id` the two scopes are a UNION - on the deal OR at the company - and each row comes back with an `on_deal` flag. Given `deal_id` alone, the company is derived from the deal.","title":"Deal Id"},"description":"Scope to contacts linked to this deal. Combined with `company_id` the two scopes are a UNION - on the deal OR at the company - and each row comes back with an `on_deal` flag. Given `deal_id` alone, the company is derived from the deal."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuoteListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"},"post":{"tags":["Quotes"],"summary":"Create Quote Contact","description":"Create a SIGNER contact and link it to the deal and company.\n\nThe full CRM contact, so the new row is immediately usable as the signer\nrather than being a name on an email. For the finance contact a quote bills\nto, use `/quote-billing-contact`.","operationId":"create_quote_contact_quote_contacts_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteContactCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/quote-billing-contact":{"post":{"tags":["Quotes"],"summary":"Create Quote Billing Contact","description":"Create the FINANCE contact a quote bills to. Name and email only.","operationId":"create_quote_billing_contact_quote_billing_contact_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteBillingContactCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/quotes/payment-installments":{"post":{"tags":["Quotes"],"summary":"Preview Payment Installments","description":"Installment amounts from percentages, and the balance left. Arithmetic over the body.\n\nReads nothing and writes nothing; persist installments through the create or\nupdate quote routes. `remaining_cents` is the part of `total_cents` the\ninstallments do not cover.","operationId":"preview_payment_installments_quotes_payment_installments_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuotePaymentInstallmentsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/quotes/approvals/pending":{"get":{"tags":["Quotes"],"summary":"List Quotes Pending Approval","description":"Quotes waiting for an approver, newest request first. Approvers only (403 otherwise).\n\n`has_more` says whether another page exists.","operationId":"list_quotes_pending_approval_quotes_approvals_pending_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"description":"Quotes per page.","default":100,"title":"Limit"},"description":"Quotes per page."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Quotes to skip.","default":0,"title":"Offset"},"description":"Quotes to skip."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuoteListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}/request-approval":{"post":{"tags":["Quotes"],"summary":"Request Quote Approval","description":"Submit an out-of-policy draft for approval without trying to send it.\n\nIdempotent while the request is pending. A quote inside the discount and\nmargin policy answers 409 `approval_not_required`: send it instead.","operationId":"request_quote_approval_quotes__quote_id__request_approval_post","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Quote id (UUID).","title":"Quote Id"},"description":"Quote id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}/approve":{"post":{"tags":["Quotes"],"summary":"Approve Quote","description":"Approve a quote that is waiting for approval. Only the approver role, or an Admin or Owner.\n\nThis only unblocks the send; nothing is sent. 409 `not_pending_approval` when\nthe quote is not waiting, 403 `not_quote_approver` for anyone else, and 403\n`own_approval_request` for whoever requested it.","operationId":"approve_quote_quotes__quote_id__approve_post","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Quote id (UUID).","title":"Quote Id"},"description":"Quote id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteApprovalDecisionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}/reject":{"post":{"tags":["Quotes"],"summary":"Reject Quote","description":"Reject a quote that is waiting for approval. A reason is required (400 without `comment`).\n\nThe quote stays an editable draft with `approval_status` `rejected`, which\nblocks sending until the rep revises it. Same approver rules as approve.","operationId":"reject_quote_quotes__quote_id__reject_post","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Quote id (UUID).","title":"Quote Id"},"description":"Quote id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteApprovalDecisionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}/signer-change/approve":{"post":{"tags":["Quotes"],"summary":"Approve Signer Change","description":"Approve the buyer's pending signer change: the new signer is sent the signing link.\n\nNeeds write access to the quote AND being its owner or an organisation\nadmin (403 `not_quote_owner_or_admin`). The buyer who asked, or the person\nnamed, can never decide it (403 `own_request`). Approving twice returns the\nsame quote.","operationId":"approve_signer_change_quotes__quote_id__signer_change_approve_post","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Quote id (UUID).","title":"Quote Id"},"description":"Quote id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignerChangeDecisionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}/signer-change/reject":{"post":{"tags":["Quotes"],"summary":"Reject Signer Change","description":"Reject the buyer's pending signer change: the signer stays and the buyer is told why.\n\nSame deciders and errors as approving it.","operationId":"reject_signer_change_quotes__quote_id__signer_change_reject_post","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","description":"Quote id (UUID).","title":"Quote Id"},"description":"Quote id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignerChangeDecisionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/quote-catalog":{"get":{"tags":["Quotes"],"summary":"Get Quote Catalog","description":"The product catalog the quote builder picks from: active, quotable products with price, cost and category.\n\n`flat` and `search` return `{items, total, page, limit}`; `grouped` returns\n`{groups, total, truncated}` (unpaged, capped at 2,000 rows). `search`\nwithout `q` is a 422.","operationId":"get_quote_catalog_quote_catalog_get","parameters":[{"name":"mode","in":"query","required":false,"schema":{"enum":["flat","grouped","search"],"type":"string","description":"flat (paged), grouped (by category) or search.","default":"flat","title":"Mode"},"description":"flat (paged), grouped (by category) or search."},{"name":"q","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"description":"Search text (name or SKU). Required for mode=search.","title":"Q"},"description":"Search text (name or SKU). Required for mode=search."},{"name":"category","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Category"}},{"name":"region","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":40},{"type":"null"}],"description":"Region code for the price multiplier.","title":"Region"},"description":"Region code for the price multiplier."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/quote-catalog/bundles":{"get":{"tags":["Quotes"],"summary":"Get Quote Catalog Bundles","description":"The curated product bundles, each resolved to catalog items.\n\nObeys the same visibility as the catalog: a product hidden there never shows up priced inside a bundle.","operationId":"get_quote_catalog_bundles_quote_catalog_bundles_get","parameters":[{"name":"region","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":40},{"type":"null"}],"description":"Region code for the price multiplier.","title":"Region"},"description":"Region code for the price multiplier."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/quote-catalog/validate":{"post":{"tags":["Quotes"],"summary":"Validate Quote Catalog Selection","description":"Check a product selection against the catalog's rules. Returns `{issues: string[]}`; empty means valid.\n\nReads only. A `manual_product_id` that does not resolve to a live product\nof this organisation is reported as an unknown-product issue, never\nsilently dropped.","operationId":"validate_quote_catalog_selection_quote_catalog_validate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteCatalogValidateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_QuotePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/stripe/api-key":{"post":{"tags":["Quotes"],"summary":"Connect Stripe Api Key","description":"Connect Stripe with a restricted API key. REACHES STRIPE to validate it.\n\nReplaces any key already stored for the org. The key is write-only: the\nresponse carries the connection id and whether it is a live-mode key,\nnever the key. Products sync within fifteen minutes, or immediately with\n`POST /stripe/sync`.","operationId":"connect_stripe_api_key_stripe_api_key_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StripeApiKeyRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/stripe/integration-status":{"get":{"tags":["Quotes"],"summary":"Get Stripe Integration Status","description":"Whether the quote catalogue is ready: `state` is one of `needs_catalog`,\n`syncing`, `no_quotable_products` or `ready`, counted across Stripe AND the\nmanual catalogue.","operationId":"get_stripe_integration_status_stripe_integration_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/stripe/sync":{"post":{"tags":["Quotes"],"summary":"Trigger Stripe Sync","description":"Sync the org's Stripe catalogue now instead of waiting for the schedule.\n\n404 when Stripe is not connected. For a large catalogue, poll\n`GET /stripe/integration-status` and watch `total_products` grow.","operationId":"trigger_stripe_sync_stripe_sync_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/stripe/connections/{connection_id}/data":{"get":{"tags":["Quotes"],"summary":"Get Stripe Data","description":"Recent customers, subscriptions, invoices and charges, read LIVE from Stripe.\n\n`connection_id` must be the org's own stored connection - any other id is\na 404, because connection ids are guessable.","operationId":"get_stripe_data_stripe_connections__connection_id__data_get","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The org's Stripe connection id.","title":"Connection Id"},"description":"The org's Stripe connection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/stripe/connections/{connection_id}/data/{resource}":{"get":{"tags":["Quotes"],"summary":"Get Stripe Data Page","description":"One page of a Stripe list, read live. Cursor-paged: pass `next_cursor`\nback as `starting_after`; `has_more` false means the last page.","operationId":"get_stripe_data_page_stripe_connections__connection_id__data__resource__get","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The org's Stripe connection id.","title":"Connection Id"},"description":"The org's Stripe connection id."},{"name":"resource","in":"path","required":true,"schema":{"enum":["customers","subscriptions","invoices","charges"],"type":"string","description":"Which Stripe list to page through.","title":"Resource"},"description":"Which Stripe list to page through."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":20,"title":"Limit"}},{"name":"starting_after","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"description":"`next_cursor` from the previous page.","title":"Starting After"},"description":"`next_cursor` from the previous page."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/stripe/products":{"get":{"tags":["Quotes"],"summary":"List Stripe Products","description":"Synced Stripe products with price range, subscriber counts and MRR.","operationId":"list_stripe_products_stripe_products_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"1-based page.","default":1,"title":"Page"},"description":"1-based page."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"filter_model","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Grid filter model as JSON, as the app's grid sends it.","title":"Filter Model"},"description":"Grid filter model as JSON, as the app's grid sends it."},{"name":"sort_model","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Grid sort model as JSON.","title":"Sort Model"},"description":"Grid sort model as JSON."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/stripe/products/{product_id}/subscribers":{"get":{"tags":["Quotes"],"summary":"List Stripe Product Subscribers","description":"Customers subscribed to one product, with the graph8 company each maps to.","operationId":"list_stripe_product_subscribers_stripe_products__product_id__subscribers_get","parameters":[{"name":"product_id","in":"path","required":true,"schema":{"type":"string","description":"Stripe product id.","title":"Product Id"},"description":"Stripe product id."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"1-based page.","default":1,"title":"Page"},"description":"1-based page."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"filter_model","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Grid filter model as JSON, as the app's grid sends it.","title":"Filter Model"},"description":"Grid filter model as JSON, as the app's grid sends it."},{"name":"sort_model","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Grid sort model as JSON.","title":"Sort Model"},"description":"Grid sort model as JSON."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/stripe/customers/{customer_id}/mapping":{"patch":{"tags":["Quotes"],"summary":"Update Stripe Customer Mapping","description":"Map a Stripe customer to a graph8 company by hand, or unmap it with null.\n\nA manual mapping is recorded as such, so the automatic matcher leaves it alone.","operationId":"update_stripe_customer_mapping_stripe_customers__customer_id__mapping_patch","parameters":[{"name":"customer_id","in":"path","required":true,"schema":{"type":"integer","description":"The synced customer row id (not the `cus_` id).","title":"Customer Id"},"description":"The synced customer row id (not the `cus_` id)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CustomerMappingRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"quotes:write","x-graph8-lifecycle":"active"}},"/stripe/companies/{company_id}/subscriptions":{"get":{"tags":["Quotes"],"summary":"Get Company Stripe Subscriptions","description":"A company's current Stripe subscriptions, through its customer mapping.","operationId":"get_company_stripe_subscriptions_stripe_companies__company_id__subscriptions_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","title":"Company Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/stripe/companies/{company_id}/invoices":{"get":{"tags":["Quotes"],"summary":"Get Company Stripe Invoices","description":"A company's Stripe invoice history, newest first.","operationId":"get_company_stripe_invoices_stripe_companies__company_id__invoices_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","title":"Company Id"}},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"1-based page.","default":1,"title":"Page"},"description":"1-based page."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/stripe/companies/{company_id}/revenue-summary":{"get":{"tags":["Quotes"],"summary":"Get Company Revenue Summary","description":"Total paid, MRR, invoice count and customer-since date for one company.","operationId":"get_company_revenue_summary_stripe_companies__company_id__revenue_summary_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","title":"Company Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/stripe/product-settings":{"get":{"tags":["Quotes"],"summary":"List Stripe Product Settings","description":"Every synced product with its quote-builder name, category and `quotable` flag.","operationId":"list_stripe_product_settings_stripe_product_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/stripe/product-settings/bulk":{"patch":{"tags":["Quotes"],"summary":"Bulk Update Stripe Product Settings","description":"Apply the same settings to many products. Org Admin or Owner key only.","operationId":"bulk_update_stripe_product_settings_stripe_product_settings_bulk_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BulkProductSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"quotes:write","x-graph8-lifecycle":"active"}},"/stripe/product-settings/{stripe_product_id}":{"put":{"tags":["Quotes"],"summary":"Upsert Stripe Product Settings","description":"Set one product's quote-builder settings. Omitted fields are left\nunchanged. Org Admin or Owner key only.","operationId":"upsert_stripe_product_settings_stripe_product_settings__stripe_product_id__put","parameters":[{"name":"stripe_product_id","in":"path","required":true,"schema":{"type":"string","description":"Stripe product id.","title":"Stripe Product Id"},"description":"Stripe product id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProductSettingsUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"quotes:write","x-graph8-lifecycle":"active"}},"/manual-products":{"get":{"tags":["Quotes"],"summary":"List Manual Products","description":"The org's own product catalogue - quotable with or without Stripe.","operationId":"list_manual_products_manual_products_get","parameters":[{"name":"include_inactive","in":"query","required":false,"schema":{"type":"boolean","description":"Include inactive products.","default":false,"title":"Include Inactive"},"description":"Include inactive products."},{"name":"include_non_quotable","in":"query","required":false,"schema":{"type":"boolean","description":"Include products not offered on quotes.","default":true,"title":"Include Non Quotable"},"description":"Include products not offered on quotes."},{"name":"category","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Category"}},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"1-based page.","default":1,"title":"Page"},"description":"1-based page."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"},"post":{"tags":["Quotes"],"summary":"Create Manual Product","description":"Add a product to the manual catalogue. Org Admin or Owner key only.","operationId":"create_manual_product_manual_products_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ManualProductCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"quotes:write","x-graph8-lifecycle":"active"}},"/manual-products/{product_id}":{"patch":{"tags":["Quotes"],"summary":"Update Manual Product","description":"Change some fields of a manual product. Only the fields you send change.","operationId":"update_manual_product_manual_products__product_id__patch","parameters":[{"name":"product_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Manual product id.","title":"Product Id"},"description":"Manual product id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ManualProductUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"quotes:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Quotes"],"summary":"Delete Manual Product","description":"Retire a manual product. A soft delete: line items on existing quotes keep it.","operationId":"delete_manual_product_manual_products__product_id__delete","parameters":[{"name":"product_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Manual product id.","title":"Product Id"},"description":"Manual product id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"quotes:delete","x-graph8-lifecycle":"active"}},"/quotes/mailbox-capacity":{"post":{"tags":["Quotes"],"summary":"Calculate Mailbox Capacity","description":"Mailboxes and domains needed to reach `contacts_per_month`, for a 30-,\n7- and 1-day delivery window, with their cost. ARITHMETIC ONLY: nothing is\nbought or written. POST only because the inputs are a body.","operationId":"calculate_mailbox_capacity_quotes_mailbox_capacity_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MailboxCapacityRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}/evidence":{"post":{"tags":["Quotes"],"summary":"Upload Quote Evidence","description":"Attach an internal PDF to a quote - for example a copy signed outside\ngraph8. Internal: it never enters the template or signing pipeline.\n\nNeeds WRITE access to the quote. 400 for anything that is not a complete\nPDF, 413 above 10 MB.","operationId":"upload_quote_evidence_quotes__quote_id__evidence_post","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Quote id.","title":"Quote Id"},"description":"Quote id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_quote_evidence_quotes__quote_id__evidence_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"quotes:write","x-graph8-lifecycle":"active"},"get":{"tags":["Quotes"],"summary":"List Quote Evidence","description":"The PDFs attached to a quote, newest first.","operationId":"list_quote_evidence_quotes__quote_id__evidence_get","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Quote id.","title":"Quote Id"},"description":"Quote id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/quotes/{quote_id}/evidence/{evidence_id}":{"get":{"tags":["Quotes"],"summary":"Download Quote Evidence","description":"A download URL for one attached PDF. The URL expires after 60 seconds.","operationId":"download_quote_evidence_quotes__quote_id__evidence__evidence_id__get","parameters":[{"name":"quote_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Quote id.","title":"Quote Id"},"description":"Quote id."},{"name":"evidence_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Evidence id.","title":"Evidence Id"},"description":"Evidence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BillingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/sales-coach/calls":{"get":{"tags":["Sales Coach"],"summary":"List Calls","description":"Practice calls, newest first, with their scores and transcript segments.","operationId":"list_calls_sales_coach_calls_get","parameters":[{"name":"email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Whose calls to read. Omit for the key owner's own. Naming SOMEBODY ELSE is manager-only and comes back 403 otherwise - calls carry transcripts and scores.","title":"Email"},"description":"Whose calls to read. Omit for the key owner's own. Naming SOMEBODY ELSE is manager-only and comes back 403 otherwise - calls carry transcripts and scores."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"post":{"tags":["Sales Coach"],"summary":"Create Call","description":"Open a practice call record.\n\nThis is the ROW, not the conversation: it is what a transcript, a score and\nan interview attempt all attach to. It does not start anything or reach\nanybody.","operationId":"create_call_sales_coach_calls_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateCallRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/sales-coach/calls/{call_id}":{"get":{"tags":["Sales Coach"],"summary":"Get Call","description":"One practice call. Owner-or-manager gated, same as the list.","operationId":"get_call_sales_coach_calls__call_id__get","parameters":[{"name":"call_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Call id (UUID).","title":"Call Id"},"description":"Call id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"put":{"tags":["Sales Coach"],"summary":"Update Call","description":"Amend a call record.\n\n`final_score` is the number a leaderboard reads, so writing it here changes\nwhat the team ranking shows. Only the fields you send are written.","operationId":"update_call_sales_coach_calls__call_id__put","parameters":[{"name":"call_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Call id (UUID).","title":"Call Id"},"description":"Call id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateCallRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Sales Coach"],"summary":"Delete Call","description":"Delete a practice call, with its transcript and scores.\n\nOwner-or-manager gated. Anything that ranked this call - a leaderboard, an\ninterview attempt - loses it, so a score that was on the board disappears\nfrom it.","operationId":"delete_call_sales_coach_calls__call_id__delete","parameters":[{"name":"call_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Call id (UUID).","title":"Call Id"},"description":"Call id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"team:delete","x-graph8-lifecycle":"active"}},"/sales-coach/calls/{call_id}/transcript":{"get":{"tags":["Sales Coach"],"summary":"Get Call Transcript","description":"What was actually said, segment by segment.\n\nOwner-or-manager gated for the same reason the call is: this is the most\nrevealing artifact the feature holds.","operationId":"get_call_transcript_sales_coach_calls__call_id__transcript_get","parameters":[{"name":"call_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Call id (UUID).","title":"Call Id"},"description":"Call id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/sales-coach/calls/{call_id}/audio-url":{"get":{"tags":["Sales Coach"],"summary":"Get Call Audio Url","description":"A time-limited link to the call recording.\n\nThe URL is signed and expires: treat it as the credential it is, not as a\npermanent address to store. The gate runs BEFORE the link is minted, so a\ncaller who may not read the call never receives one.","operationId":"get_call_audio_url_sales_coach_calls__call_id__audio_url_get","parameters":[{"name":"call_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Call id (UUID).","title":"Call Id"},"description":"Call id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/sales-coach/contact-lists":{"get":{"tags":["Sales Coach"],"summary":"List Coach Contact Lists","description":"Audiences a practice call or interview round can draw a prospect from.","operationId":"list_coach_contact_lists_sales_coach_contact_lists_get","parameters":[{"name":"only_tagged","in":"query","required":false,"schema":{"type":"boolean","description":"Only lists tagged for coaching, rather than every audience.","default":false,"title":"Only Tagged"},"description":"Only lists tagged for coaching, rather than every audience."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/sales-coach/prospects/search":{"get":{"tags":["Sales Coach"],"summary":"Search Coach Prospects","description":"Find the prospect the AI will play.\n\nPaginated, because an audience is routinely larger than a picker: `offset`\nplus `limit` rather than a page number, matching the app.","operationId":"search_coach_prospects_sales_coach_prospects_search_get","parameters":[{"name":"audience_id","in":"query","required":true,"schema":{"type":"string","description":"Audience to search within.","title":"Audience Id"},"description":"Audience to search within."},{"name":"q","in":"query","required":false,"schema":{"type":"string","description":"Free text over the prospect's name and company.","default":"","title":"Q"},"description":"Free text over the prospect's name and company."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/sales-coach/interviews":{"get":{"tags":["Sales Coach"],"summary":"List Interviews","description":"Every interview round in the organisation.","operationId":"list_interviews_sales_coach_interviews_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"post":{"tags":["Sales Coach"],"summary":"Create Interview","description":"Create an interview round.\n\nCreating it invites nobody. Members are added separately, and only then can\nan invite go out.","operationId":"create_interview_sales_coach_interviews_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateInterviewRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/sales-coach/interviews/by-code/{code}":{"get":{"tags":["Sales Coach"],"summary":"Get Interview By Code","description":"Resolve an invite code to the round it belongs to.\n\nPublished as `by-code` rather than the app's `code` so it reads the same\nway as `/interview-attempts/by-code/{code}` - the app spells the same idea\ntwo ways and a public contract should not inherit that.","operationId":"get_interview_by_code_sales_coach_interviews_by_code__code__get","parameters":[{"name":"code","in":"path","required":true,"schema":{"type":"string","description":"A member's invite code.","title":"Code"},"description":"A member's invite code."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/sales-coach/interviews/{interview_id}":{"get":{"tags":["Sales Coach"],"summary":"Get Interview","description":"One interview round, with its members.","operationId":"get_interview_sales_coach_interviews__interview_id__get","parameters":[{"name":"interview_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Interview round id (UUID).","title":"Interview Id"},"description":"Interview round id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Sales Coach"],"summary":"Delete Interview","description":"Delete an interview round.\n\nIts members' invite codes stop resolving, so anyone holding a link that has\nnot been used yet loses it.","operationId":"delete_interview_sales_coach_interviews__interview_id__delete","parameters":[{"name":"interview_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Interview round id (UUID).","title":"Interview Id"},"description":"Interview round id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"team:delete","x-graph8-lifecycle":"active"}},"/sales-coach/interviews/{interview_id}/members":{"post":{"tags":["Sales Coach"],"summary":"Add Interview Member","description":"Add someone to an interview round and mint their invite code.\n\n`send_invite=true` EMAILS THAT PERSON. It defaults to false, so adding a\nmember is by default a quiet write and the mail is a separate decision -\nwhich is what makes it safe to build a whole round before anybody hears\nabout it.","operationId":"add_interview_member_sales_coach_interviews__interview_id__members_post","parameters":[{"name":"interview_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Interview round id (UUID).","title":"Interview Id"},"description":"Interview round id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AddInterviewMemberRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"team:run","x-graph8-lifecycle":"active"}},"/sales-coach/interviews/{interview_id}/members/{member_id}/send-invite":{"post":{"tags":["Sales Coach"],"summary":"Send Interview Invite","description":"Send - or re-send - a member's invite email. THIS REACHES A REAL PERSON.\n\nTiered `external` rather than `write` for that reason: a customer can hand\nout \"build interview rounds\" without handing out \"email my candidates\".","operationId":"send_interview_invite_sales_coach_interviews__interview_id__members__member_id__send_invite_post","parameters":[{"name":"interview_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Interview round id (UUID).","title":"Interview Id"},"description":"Interview round id (UUID)."},{"name":"member_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Member id (UUID).","title":"Member Id"},"description":"Member id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"team:run","x-graph8-lifecycle":"active"}},"/sales-coach/interview-attempts":{"get":{"tags":["Sales Coach"],"summary":"List Interview Attempts","description":"Who sat an interview round, and against which call.","operationId":"list_interview_attempts_sales_coach_interview_attempts_get","parameters":[{"name":"call_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"description":"Only attempts made of this call.","title":"Call Id"},"description":"Only attempts made of this call."},{"name":"member_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"description":"Only this member's attempts.","title":"Member Id"},"description":"Only this member's attempts."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"post":{"tags":["Sales Coach"],"summary":"Create Interview Attempt","description":"Attach an existing call to an interview round as an attempt.\n\nThe call must already exist - this records that it COUNTED, it does not\ncreate it. Create the call first with `POST /sales-coach/calls`.","operationId":"create_interview_attempt_sales_coach_interview_attempts_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateInterviewAttemptRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/sales-coach/interview-attempts/by-code/{code}":{"post":{"tags":["Sales Coach"],"summary":"Create Interview Attempt By Code","description":"Record an attempt identified by the member's CODE rather than their id.\n\nThe path a candidate flow uses, where the code is the only thing on hand.\nAn EXPIRED code is a 410, not a 404 - the distinction matters, because a\n410 means \"this was real and the window closed\" and is worth re-inviting\nfor, while a 404 means the code never existed.","operationId":"create_interview_attempt_by_code_sales_coach_interview_attempts_by_code__code__post","parameters":[{"name":"code","in":"path","required":true,"schema":{"type":"string","description":"The member's invite code. Matched case-insensitively.","title":"Code"},"description":"The member's invite code. Matched case-insensitively."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateInterviewAttemptByCodeRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CoachPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/sales-coach/leaderboard":{"get":{"tags":["Sales Coach"],"summary":"Get Sales Coach Leaderboard","description":"The coaching leaderboard: every rep, ranked.\n\nThis is the module's own board, distinct from the CONFIGURABLE boards\nunder `/team/leaderboards` - it takes no configuration and no period.","operationId":"get_sales_coach_leaderboard_sales_coach_leaderboard_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/sales-coach/team/bootstrap":{"get":{"tags":["Sales Coach"],"summary":"Get Team Bootstrap","description":"Everything a Team HQ screen needs in ONE call.\n\nThe boards, the sets, the config and the first page of data together.\nBuilt for a display that would otherwise make five round trips before it\ncan render anything, and it is the right call for a dashboard rebuilding\nthis rather than fetching each piece.","operationId":"get_team_bootstrap_sales_coach_team_bootstrap_get","parameters":[{"name":"period","in":"query","required":false,"schema":{"type":"string","description":"Window to score over. `today` is the app's default; the values a given org accepts come back in `visible_periods` from `GET /sales-coach/team/config`, because the set is configurable.","default":"today","title":"Period"},"description":"Window to score over. `today` is the app's default; the values a given org accepts come back in `visible_periods` from `GET /sales-coach/team/config`, because the set is configurable."},{"name":"lb","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Leaderboard to open on.","title":"Lb"},"description":"Leaderboard to open on."},{"name":"set","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Rotation to open on. The wire name is `set`, matching the app's `?set=` query parameter; `set` is a Python builtin, so the handler parameter is `set_id` and the alias keeps the wire name identical to the app's.","title":"Set"},"description":"Rotation to open on. The wire name is `set`, matching the app's `?set=` query parameter; `set` is a Python builtin, so the handler parameter is `set_id` and the alias keeps the wire name identical to the app's."},{"name":"role","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Legacy fallback when neither `lb` nor `set` is given.","title":"Role"},"description":"Legacy fallback when neither `lb` nor `set` is given."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/sales-coach/team/leaderboards":{"get":{"tags":["Sales Coach"],"summary":"List Team Leaderboards","description":"Every configured leaderboard, including the ones the product ships.","operationId":"list_team_leaderboards_sales_coach_team_leaderboards_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"post":{"tags":["Sales Coach"],"summary":"Create Team Leaderboard","description":"Create a leaderboard.\n\n`id` is caller-chosen, matching the app: these are config rows keyed by a\nslug you pick, and POSTing an id that already exists UPSERTS rather than\nfailing. Said plainly because a caller retrying a create would otherwise\nassume a duplicate was rejected.\n\nRequires team-floor management: org Owner/Admin, or an explicit\n`sales_manager` assignment.","operationId":"create_team_leaderboard_sales_coach_team_leaderboards_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LeaderboardConfigRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/sales-coach/team/leaderboards/{lb_id}":{"put":{"tags":["Sales Coach"],"summary":"Update Team Leaderboard","description":"Replace a leaderboard's configuration.\n\nA PUT, matching the app: the body is the board's new state, so a KPI you\nomit is REMOVED from the board rather than left alone.","operationId":"update_team_leaderboard_sales_coach_team_leaderboards__lb_id__put","parameters":[{"name":"lb_id","in":"path","required":true,"schema":{"type":"string","description":"Leaderboard id.","title":"Lb Id"},"description":"Leaderboard id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LeaderboardConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Sales Coach"],"summary":"Delete Team Leaderboard","description":"Delete a leaderboard.\n\nThe app answers 204 with no body. This returns `{\"deleted\": true}` in the\nstandard envelope instead, because every other operation on this contract\nreturns one and a client that special-cased an empty body here would be\nthe only place it had to.","operationId":"delete_team_leaderboard_sales_coach_team_leaderboards__lb_id__delete","parameters":[{"name":"lb_id","in":"path","required":true,"schema":{"type":"string","description":"Leaderboard id.","title":"Lb Id"},"description":"Leaderboard id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"team:delete","x-graph8-lifecycle":"active"}},"/sales-coach/team/leaderboards/{lb_id}/data":{"get":{"tags":["Sales Coach"],"summary":"Get Team Leaderboard Data","description":"The scores: one row per rep, one column per KPI on the board.\n\nOpen-shaped, because the columns are whichever KPIs the board is\nconfigured with - including a customer's own. A closed model would drop\none, and a missing column reads as a rep having scored nothing.","operationId":"get_team_leaderboard_data_sales_coach_team_leaderboards__lb_id__data_get","parameters":[{"name":"lb_id","in":"path","required":true,"schema":{"type":"string","description":"Leaderboard id.","title":"Lb Id"},"description":"Leaderboard id."},{"name":"period","in":"query","required":false,"schema":{"type":"string","description":"Window to score over. `today` is the app's default; the values a given org accepts come back in `visible_periods` from `GET /sales-coach/team/config`, because the set is configurable.","default":"today","title":"Period"},"description":"Window to score over. `today` is the app's default; the values a given org accepts come back in `visible_periods` from `GET /sales-coach/team/config`, because the set is configurable."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/sales-coach/team/sets":{"get":{"tags":["Sales Coach"],"summary":"List Team Sets","description":"Configured rotations.","operationId":"list_team_sets_sales_coach_team_sets_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"post":{"tags":["Sales Coach"],"summary":"Create Team Set","description":"Create a rotation of leaderboards. Caller-chosen `id`, same as boards.","operationId":"create_team_set_sales_coach_team_sets_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetConfigRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/sales-coach/team/sets/{set_id}":{"put":{"tags":["Sales Coach"],"summary":"Update Team Set","description":"Replace a rotation. A PUT: an omitted board leaves the rotation.","operationId":"update_team_set_sales_coach_team_sets__set_id__put","parameters":[{"name":"set_id","in":"path","required":true,"schema":{"type":"string","description":"Set id.","title":"Set Id"},"description":"Set id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Sales Coach"],"summary":"Delete Team Set","description":"Delete a rotation. The leaderboards in it are untouched.","operationId":"delete_team_set_sales_coach_team_sets__set_id__delete","parameters":[{"name":"set_id","in":"path","required":true,"schema":{"type":"string","description":"Set id.","title":"Set Id"},"description":"Set id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"team:delete","x-graph8-lifecycle":"active"}},"/sales-coach/team/sets/{set_id}/data":{"get":{"tags":["Sales Coach"],"summary":"Get Team Set Data","description":"Every board in the rotation, scored, in one call.","operationId":"get_team_set_data_sales_coach_team_sets__set_id__data_get","parameters":[{"name":"set_id","in":"path","required":true,"schema":{"type":"string","description":"Set id.","title":"Set Id"},"description":"Set id."},{"name":"period","in":"query","required":false,"schema":{"type":"string","description":"Window to score over. `today` is the app's default; the values a given org accepts come back in `visible_periods` from `GET /sales-coach/team/config`, because the set is configurable.","default":"today","title":"Period"},"description":"Window to score over. `today` is the app's default; the values a given org accepts come back in `visible_periods` from `GET /sales-coach/team/config`, because the set is configurable."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/sales-coach/team/config":{"get":{"tags":["Sales Coach"],"summary":"Get Team Config","description":"Team Command Center settings: visible columns, periods, goals, rotation.\n\nRead this before scoring anything: `visible_periods` is the set of values\nthe `period` query parameter accepts for THIS org.","operationId":"get_team_config_sales_coach_team_config_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"put":{"tags":["Sales Coach"],"summary":"Update Team Config","description":"Change Team Command Center settings. Team-floor management required.\n\nThe body is OPEN, mirroring the app's own model: this config is a JSONB bag\nthat grows, and its DTO carries `extra=\"allow\"` with a comment calling that\nan intentional deviation. Closing it here would reject a key the app\nitself stores.","operationId":"update_team_config_sales_coach_team_config_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TeamConfigUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/sales-coach/team/kpi-catalog":{"get":{"tags":["Sales Coach"],"summary":"Get Team Kpi Catalog","description":"Every KPI a leaderboard can be built from, with its default weight.\n\nThe source of the `id` values a leaderboard's `kpis` refer to - build a\nboard from anything else and it scores nothing.","operationId":"get_team_kpi_catalog_sales_coach_team_kpi_catalog_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/sales-coach/team/roles":{"get":{"tags":["Sales Coach"],"summary":"List Team Roles","description":"The Team HQ roles, and who holds them.","operationId":"list_team_roles_sales_coach_team_roles_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/sales-coach/team/active-users-summary":{"get":{"tags":["Sales Coach"],"summary":"Get Team Active Users Summary","description":"Who is active, and who can be put on a board.","operationId":"get_team_active_users_summary_sales_coach_team_active_users_summary_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/sales-coach/team/users/{user_id}/role":{"put":{"tags":["Sales Coach"],"summary":"Assign Team Role","description":"Grant a Team HQ role. THIS REPLACES THE PERSON'S PERMISSIONS.\n\n`cb_user_roles` has a composite primary key on (user_id, org_id), so the\nnew row replaces whatever they had - this is a privilege grant, not a\nlabel on a dashboard.\n\nThe app's three rules apply unchanged and each is a 403:\n\n  * the caller must be able to manage the team floor;\n  * no self-assignment, or a manager could re-role themselves;\n  * the caller must already hold every permission of the role they are\n    granting, unless they are an org Owner or Admin - Settings'\n    non-escalation rule.\n\nOnly the five Team HQ slugs are assignable. `admin` is not one of them and\nis refused at the request layer.","operationId":"assign_team_role_sales_coach_team_users__user_id__role_put","parameters":[{"name":"user_id","in":"path","required":true,"schema":{"type":"string","description":"The member to re-role.","title":"User Id"},"description":"The member to re-role."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssignTeamRoleRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TeamPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"team:delete","x-graph8-lifecycle":"active"}},"/roles/permissions":{"get":{"tags":["Roles"],"summary":"List Permissions","description":"Every permission a role can be built from.\n\nThe source of the strings `POST /roles` and `PUT /roles/{role_id}` accept\nin `permissions`. Read this first: a permission the org does not have is\nrejected, and the app's non-escalation guard additionally refuses anything\nthe CALLER does not already hold.","operationId":"list_permissions_roles_permissions_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/roles/permissions/grouped":{"get":{"tags":["Roles"],"summary":"List Permissions Grouped","description":"The same catalogue, bucketed by the product area each permission gates.\n\nThe shape a permission picker is built from. Open-shaped: the buckets grow\nas the product does, and a dropped one would read as \"that area has no\npermissions\" rather than \"we did not tell you\".","operationId":"list_permissions_grouped_roles_permissions_grouped_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/roles/options":{"get":{"tags":["Roles"],"summary":"List Role Options","description":"Roles as a PICKER: id, name, slug. No permission lists.\n\nDeliberately ungated, matching the app: choosing a role from a list is not\nan administrative act, and gating it is what made the picker render empty\nfor every ordinary member.","operationId":"list_role_options_roles_options_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/roles/org-users":{"get":{"tags":["Roles"],"summary":"List Org Users","description":"Everyone in the organisation, with the role each of them holds.\n\nThe join between the identity provider's membership list and this org's\nown role assignments - which is the only place both halves appear\ntogether.\n\nOn the app's ungated sibling router, so no admin gate here either: the\ndirectory is what every owner and assignee picker in the product is built\nfrom, and `settings:read` OR `team:read` is the app's own bar for it.","operationId":"list_org_users_roles_org_users_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/roles/me/permissions":{"get":{"tags":["Roles"],"summary":"Get My Permissions","description":"What THIS KEY may do, as the app's own permission machinery sees it.\n\nWorth calling before anything else on this surface: the non-escalation\nguard on every write below bounds what you may grant by what this answer\ncontains. A machine key with no human behind it holds no role permissions\nand will see an empty set - that is the documented fail-closed policy, not\na lookup failure.","operationId":"get_my_permissions_roles_me_permissions_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/roles/domain-settings":{"get":{"tags":["Roles"],"summary":"Get Domain Settings","description":"Which email domains can reach this organisation, and how.\n\n`domain_autojoin` is the consequential field: with it on, anybody with an\naddress at one of these domains joins automatically, at\n`autojoin_default_role_id`. The WRITE half of this is not published - see\nthe module docstring.","operationId":"get_domain_settings_roles_domain_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/roles/join-requests":{"get":{"tags":["Roles"],"summary":"List Join Requests","description":"People waiting to be let into the organisation.\n\nRead-only here. Approving or rejecting one admits a human being to the\ntenant and can make them an administrator of it, so it stays in the\nproduct - see the module docstring.","operationId":"list_join_requests_roles_join_requests_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Queue state to list: `pending`, `approved` or `rejected`.","default":"pending","title":"Status"},"description":"Queue state to list: `pending`, `approved` or `rejected`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/roles/join-requests/count":{"get":{"tags":["Roles"],"summary":"Get Join Request Count","description":"How many people are waiting. The cheap poll behind a queue badge.\n\nDeclared BEFORE `/roles/{role_id}` so the literal wins - that route parses\na UUID, so a flip would answer 422 rather than 404, which is much harder\nto recognise as a routing problem.","operationId":"get_join_request_count_roles_join_requests_count_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/roles/join-requests/{request_id}/reject":{"post":{"tags":["Roles"],"summary":"Reject Join Request","description":"Turn a pending join request down. Nobody gains access.\n\nPublished although its twin `approve` is not, for the same reason\n`DELETE /roles/pending-invites/{email}` is: this direction only ever\nREFUSES access, and the direction that admits a person - possibly at an\nOwner or Admin role - is the one that needs a human.\n\n400 when the request is no longer pending; 404 when it is not this\norganisation's.","operationId":"reject_join_request_roles_join_requests__request_id__reject_post","parameters":[{"name":"request_id","in":"path","required":true,"schema":{"type":"string","description":"Join request id (UUID).","title":"Request Id"},"description":"Join request id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/roles/pending-invites":{"get":{"tags":["Roles"],"summary":"List Pending Invites","description":"Invitations sent but not yet accepted, and the role each one carries.\n\nAn invitation is a role assignment that has not landed yet: the role is\napplied on the invitee's first login. That makes this list the honest\nanswer to \"who is about to get access, and to what\".","operationId":"list_pending_invites_roles_pending_invites_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/roles/pending-invites/{email}":{"delete":{"tags":["Roles"],"summary":"Revoke Pending Invite","description":"Withdraw an invitation before it is accepted.\n\nPublished although its counterpart `POST /invite` is not, and the\nasymmetry is deliberate: this only ever REMOVES a pending grant. The\ndirection that hands someone access is the one that needs a human.","operationId":"revoke_pending_invite_roles_pending_invites__email__delete","parameters":[{"name":"email","in":"path","required":true,"schema":{"type":"string","description":"Email address the invitation was sent to.","title":"Email"},"description":"Email address the invitation was sent to."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"account:delete","x-graph8-lifecycle":"active"}},"/roles/invite":{"post":{"tags":["Roles"],"summary":"Invite Member","description":"Invite one person into the organisation, at a role below administrator.\n\n`status` in the response is the app's own: `invited` when an invitation\nemail went out to someone with no graph8 account, `added` when the person\nalready had one and now holds the role immediately. Re-inviting the same\naddress is safe - the pending invitation is UPDATED to the new role rather\nthan duplicated - so a reconciliation loop may call this once per row.\n\nADMINISTRATOR ROLES ARE REFUSED HERE, AND THAT IS WHY THIS ROUTE CAN EXIST\nAT ALL. The module docstring withholds every route that can end with a\nperson holding PropelAuth `Owner` or `Admin`. The reason is specific:\n`build_api_principal` can answer AS an org administrator, and the app's\n`_assert_can_grant_permissions` bypasses its non-escalation check for a\nprivileged org role - so a bare proxy of the app handler would let a\ncredential mint an administrator. Capping the role here removes exactly\nthat, and leaves the capability that was actually asked for: admitting\nmembers and project roles in bulk from a script, a workflow or an agent.\nGranting administration stays a decision for a person, in the product.\n\n422 when neither or both of `role_id`/`role` are given; 404 when the role is\nnot this organisation's; 403 when the role is administrator-equivalent, or\nwhen the app refuses the grant because the key's own permissions do not\ncover the role's.","operationId":"invite_member_roles_invite_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/InviteMemberRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"account:run","x-graph8-lifecycle":"active"}},"/roles/users/{user_id}":{"get":{"tags":["Roles"],"summary":"Get User Role","description":"The role one person holds in this organisation.\n\n404 when they hold none - which is a real state, not an error: a member\ncan exist in the organisation with no role assigned yet.\n\nThe WRITE twin, `PUT /v1/roles/users/{user_id}`, is not published. It\nmaps a role slug of `owner` or `admin` onto the identity provider's own\nOwner/Admin and syncs it, so it can make somebody an administrator of the\ntenant.","operationId":"get_user_role_roles_users__user_id__get","parameters":[{"name":"user_id","in":"path","required":true,"schema":{"type":"string","description":"Identity-provider user id.","title":"User Id"},"description":"Identity-provider user id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/roles/service-provider/assignments":{"get":{"tags":["Roles"],"summary":"List Service Provider Assignments","description":"Which lists each outside service provider can see.\n\nA service provider is a non-employee working inside the tenant, and this\nis the whole of what they are allowed to reach. Worth auditing.","operationId":"list_service_provider_assignments_roles_service_provider_assignments_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/roles/service-provider/available-lists":{"get":{"tags":["Roles"],"summary":"List Service Provider Available Lists","description":"The lists that COULD be delegated, scoped to what the caller can see.\n\nNot every list in the org: the app applies the caller's own list-read\nscope, so a manager cannot delegate a list they cannot read themselves.","operationId":"list_service_provider_available_lists_roles_service_provider_available_lists_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/roles/service-provider/assignments/{email}":{"delete":{"tags":["Roles"],"summary":"Delete Service Provider Assignments","description":"Revoke every list a service provider was given. Their access ends here.\n\nPublished although the PUT that grants assignments is not. This one only\ndeletes rows in `service_provider_list_assignments`; the PUT additionally\nRE-ROLES the named person - see the PR body.","operationId":"delete_service_provider_assignments_roles_service_provider_assignments__email__delete","parameters":[{"name":"email","in":"path","required":true,"schema":{"type":"string","description":"The service provider's email address.","title":"Email"},"description":"The service provider's email address."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"account:delete","x-graph8-lifecycle":"active"}},"/roles":{"get":{"tags":["Roles"],"summary":"List Roles","description":"Every role in the organisation, with its permissions and holder count.","operationId":"list_roles_roles_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"post":{"tags":["Roles"],"summary":"Create Role","description":"Define a new role. It grants nobody anything until it is assigned.\n\nTwo of the app's own guards run inside the handler and are not duplicated\nhere: `_assert_can_grant_permissions` refuses a permission the CALLER does\nnot hold, and `_require_teams_manage` refuses `manages_role_slugs` without\n`teams:manage`. Both reach the caller as a 403 with the app's own message.\n\nThis is `write` rather than `destructive` on purpose: a brand-new role is\nheld by no one, so creating it changes nobody's access. Editing one does -\nwhich is why `PUT /roles/{role_id}` is tiered differently.","operationId":"create_role_roles_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RoleCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/roles/{role_id}":{"get":{"tags":["Roles"],"summary":"Get Role","description":"One role, with the full permission list it grants.","operationId":"get_role_roles__role_id__get","parameters":[{"name":"role_id","in":"path","required":true,"schema":{"type":"string","description":"Role id (UUID).","title":"Role Id"},"description":"Role id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Roles"],"summary":"Update Role","description":"Redefine a role. THIS CHANGES WHAT EVERY HOLDER MAY DO, IMMEDIATELY.\n\n`permissions` REPLACES the list rather than merging into it, so a value\nleft out is a permission taken away from everyone who holds the role. That\nis why this operation is tiered `destructive` rather than `write`: it is a\nprivilege change, and \"re-define what the sales team may do\" must not ride\nalong in the same grant as \"rename a team\".\n\nThe app refuses to edit the permissions of its locked system roles\n(`admin`, `service_provider`) - stripping `roles:manage` from `admin`\nwould lock the organisation out with no recovery path - and refuses to\ngrant anything the caller does not hold. Both reach you as a 403.","operationId":"update_role_roles__role_id__put","parameters":[{"name":"role_id","in":"path","required":true,"schema":{"type":"string","description":"Role id (UUID).","title":"Role Id"},"description":"Role id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RoleUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"account:delete","x-graph8-lifecycle":"active"},"delete":{"tags":["Roles"],"summary":"Delete Role","description":"Remove a role definition.\n\nThe app refuses while anyone still holds it, so this cannot silently strip\na colleague's access - re-role them first.","operationId":"delete_role_roles__role_id__delete","parameters":[{"name":"role_id","in":"path","required":true,"schema":{"type":"string","description":"Role id (UUID).","title":"Role Id"},"description":"Role id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"account:delete","x-graph8-lifecycle":"active"}},"/teams":{"get":{"tags":["Teams"],"summary":"List Teams","description":"Every team in the organisation, with its channels and member preview.\n\nAll aggregates are computed in grouped queries, so this stays one round\ntrip however many teams there are.","operationId":"list_teams_teams_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"post":{"tags":["Teams"],"summary":"Create Team","description":"Create a team, with its members and channels, in ONE transaction.\n\nEverything in the body lands atomically: a team is never briefly visible\nwith none of its mailboxes attached, and a rejected member id rolls the\nwhole thing back rather than leaving a half-built team.\n\n409 when the name is already taken in this organisation.","operationId":"create_team_teams_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TeamCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/teams/available/agents":{"get":{"tags":["Teams"],"summary":"List Available Agents","description":"AI agents that can be put on a team.","operationId":"list_available_agents_teams_available_agents_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/teams/available/mailboxes":{"get":{"tags":["Teams"],"summary":"List Available Mailboxes","description":"Mailboxes that can be attached to a team.","operationId":"list_available_mailboxes_teams_available_mailboxes_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/teams/available/phone-numbers":{"get":{"tags":["Teams"],"summary":"List Available Phone Numbers","description":"Phone numbers that can be attached to a team.","operationId":"list_available_phone_numbers_teams_available_phone_numbers_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/teams/available/linkedin-accounts":{"get":{"tags":["Teams"],"summary":"List Available Linkedin Accounts","description":"LinkedIn sending accounts that can be attached to a team.\n\nSpans both providers the organisation may be on, and the response says\nwhich provider each account belongs to - that pair is what\n`POST /teams/{team_id}/linkedin-accounts` wants.","operationId":"list_available_linkedin_accounts_teams_available_linkedin_accounts_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/teams/available/campaigns":{"get":{"tags":["Teams"],"summary":"List Available Campaigns","description":"Campaigns that can be linked to a team.","operationId":"list_available_campaigns_teams_available_campaigns_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/teams/available/sequences":{"get":{"tags":["Teams"],"summary":"List Available Sequences","description":"Sequences that can be linked to a team.","operationId":"list_available_sequences_teams_available_sequences_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/teams/available/chatbots":{"get":{"tags":["Teams"],"summary":"List Available Chatbots","description":"Web chatbots that can be linked to a team.","operationId":"list_available_chatbots_teams_available_chatbots_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/teams/auto-compose/suggest":{"post":{"tags":["Teams"],"summary":"Auto Compose Suggest","description":"Propose a team structure from the organisation's current universe.\n\nTHIS SPENDS CREDITS. It reads every member, mailbox, number, campaign and\nsequence and runs a model over them, and the handler settles the usage\nafterwards - which is why it gates on `team:run` rather than plain write.\n\nIt SUGGESTS only. Nothing is created until you send the result to\n`POST /teams`.","operationId":"auto_compose_suggest_teams_auto_compose_suggest_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"team:run","x-graph8-lifecycle":"active"}},"/teams/{team_id}":{"get":{"tags":["Teams"],"summary":"Get Team","description":"One team, with its full membership list.","operationId":"get_team_teams__team_id__get","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"put":{"tags":["Teams"],"summary":"Update Team","description":"Update a team, and optionally re-attach everything on it in one call.\n\nAn omitted `*_ids` list LEAVES that attachment alone. A list that IS\npresent REPLACES it, so sending `[]` detaches every mailbox (or number, or\ncampaign) the team had. Omitting and sending an empty list are different\ninstructions and the second one is destructive - the handler diffs.","operationId":"update_team_teams__team_id__put","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TeamUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Teams"],"summary":"Delete Team","description":"Delete a team.\n\nEveryone who was on it loses whatever `:team`-scoped visibility the\nmembership gave them. The records themselves are untouched.","operationId":"delete_team_teams__team_id__delete","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"team:delete","x-graph8-lifecycle":"active"}},"/teams/{team_id}/members":{"post":{"tags":["Teams"],"summary":"Add Team Member","description":"Put a person on a team.\n\nThis WIDENS what they can see: every `:team`-scoped permission they hold\nnow resolves against this team's records too.","operationId":"add_team_member_teams__team_id__members_post","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TeamMemberAddRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/teams/{team_id}/members/{user_id}":{"put":{"tags":["Teams"],"summary":"Update Team Member Role","description":"Change someone's role WITHIN this team. Their previous role is gone.\n\n`cb_team_user_memberships` holds one row per (team, user), so this\nREPLACES rather than adds. Tiered `destructive` by an explicit rule\nbecause it is a privilege change - promoting a colleague to team manager\nmust not be the same grant as renaming the team.","operationId":"update_team_member_role_teams__team_id__members__user_id__put","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"user_id","in":"path","required":true,"schema":{"type":"string","description":"Identity-provider user id.","title":"User Id"},"description":"Identity-provider user id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TeamMemberRoleUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"team:delete","x-graph8-lifecycle":"active"},"delete":{"tags":["Teams"],"summary":"Remove Team Member","description":"Take a person off a team. They keep their org role; they lose the team.","operationId":"remove_team_member_teams__team_id__members__user_id__delete","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"user_id","in":"path","required":true,"schema":{"type":"string","description":"Identity-provider user id.","title":"User Id"},"description":"Identity-provider user id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"team:delete","x-graph8-lifecycle":"active"}},"/teams/{team_id}/agents":{"get":{"tags":["Teams"],"summary":"List Team Agents","description":"The AI agents that are members of this team.","operationId":"list_team_agents_teams__team_id__agents_get","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"post":{"tags":["Teams"],"summary":"Add Team Agent","description":"Put an AI agent on a team.\n\nAn agent member is scoped exactly like a human one: it sees what the team\nsees. Delegated authority is bounded by the delegator's, so an agent\ncannot be given reach the caller does not have.","operationId":"add_team_agent_teams__team_id__agents_post","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TeamMemberAddRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/teams/{team_id}/agents/{user_id}":{"patch":{"tags":["Teams"],"summary":"Update Team Agent Role","description":"Change an agent's role within this team. REPLACES the previous one.\n\nTiered `destructive` for the same reason as its human twin: it is a\nprivilege change on a membership row, not an edit to a label.","operationId":"update_team_agent_role_teams__team_id__agents__user_id__patch","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"user_id","in":"path","required":true,"schema":{"type":"string","description":"Agent user id.","title":"User Id"},"description":"Agent user id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TeamMemberRoleUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"team:delete","x-graph8-lifecycle":"active"},"delete":{"tags":["Teams"],"summary":"Remove Team Agent","description":"Take an AI agent off a team.","operationId":"remove_team_agent_teams__team_id__agents__user_id__delete","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"user_id","in":"path","required":true,"schema":{"type":"string","description":"Agent user id.","title":"User Id"},"description":"Agent user id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"team:delete","x-graph8-lifecycle":"active"}},"/teams/{team_id}/mailboxes":{"get":{"tags":["Teams"],"summary":"List Team Mailboxes","description":"The mailboxes this team may send from.","operationId":"list_team_mailboxes_teams__team_id__mailboxes_get","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"post":{"tags":["Teams"],"summary":"Assign Mailbox To Team","description":"Attach a mailbox to a team. Everyone on the team may then send from it.\n\n`object_id` is the integer `mailboxes.id` from\n`GET /teams/available/mailboxes`, not the mailbox address.","operationId":"assign_mailbox_to_team_teams__team_id__mailboxes_post","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssignObjectRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/teams/{team_id}/mailboxes/{mailbox_id}":{"delete":{"tags":["Teams"],"summary":"Unassign Mailbox From Team","description":"Detach a mailbox. The mailbox itself survives; the team loses access.","operationId":"unassign_mailbox_from_team_teams__team_id__mailboxes__mailbox_id__delete","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","description":"Integer `mailboxes.id`.","title":"Mailbox Id"},"description":"Integer `mailboxes.id`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"team:delete","x-graph8-lifecycle":"active"}},"/teams/{team_id}/phone-numbers":{"get":{"tags":["Teams"],"summary":"List Team Phone Numbers","description":"The phone numbers this team may call and text from.","operationId":"list_team_phone_numbers_teams__team_id__phone_numbers_get","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"post":{"tags":["Teams"],"summary":"Assign Phone To Team","description":"Attach a phone number to a team.","operationId":"assign_phone_to_team_teams__team_id__phone_numbers_post","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssignObjectRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/teams/{team_id}/phone-numbers/{phone_id}":{"delete":{"tags":["Teams"],"summary":"Unassign Phone From Team","description":"Detach a phone number from a team.","operationId":"unassign_phone_from_team_teams__team_id__phone_numbers__phone_id__delete","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"phone_id","in":"path","required":true,"schema":{"type":"integer","description":"Integer phone-number id.","title":"Phone Id"},"description":"Integer phone-number id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"team:delete","x-graph8-lifecycle":"active"}},"/teams/{team_id}/linkedin-accounts":{"get":{"tags":["Teams"],"summary":"List Team Linkedin Accounts","description":"The LinkedIn accounts this team may send from.","operationId":"list_team_linkedin_accounts_teams__team_id__linkedin_accounts_get","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"post":{"tags":["Teams"],"summary":"Assign Linkedin Account To Team","description":"Attach a LinkedIn sending account to a team.\n\nTwo spellings, both accepted because the app accepts both: the current\n`provider` + `account_ref` pair from\n`GET /teams/available/linkedin-accounts`, or the legacy\n`linkedin_account_id`. Send the pair for new integrations - the legacy id\nis ambiguous across providers.","operationId":"assign_linkedin_account_to_team_teams__team_id__linkedin_accounts_post","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssignLinkedInAccountRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/teams/{team_id}/linkedin-accounts/assoc/{assoc_id}":{"delete":{"tags":["Teams"],"summary":"Unassign Linkedin Account By Assoc","description":"Detach ONE association by its own id.\n\nUse this rather than the account-id form when the same account is attached\nmore than once: the account-id form removes whichever association it finds,\nand this names exactly the one you mean. Declared BEFORE the account-id\nroute so the `assoc` literal is reachable.","operationId":"unassign_linkedin_account_by_assoc_teams__team_id__linkedin_accounts_assoc__assoc_id__delete","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"assoc_id","in":"path","required":true,"schema":{"type":"string","description":"Association row id (UUID).","title":"Assoc Id"},"description":"Association row id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"team:delete","x-graph8-lifecycle":"active"}},"/teams/{team_id}/linkedin-accounts/{linkedin_account_id}":{"delete":{"tags":["Teams"],"summary":"Unassign Linkedin Account From Team","description":"Detach a LinkedIn account from a team.","operationId":"unassign_linkedin_account_from_team_teams__team_id__linkedin_accounts__linkedin_account_id__delete","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"linkedin_account_id","in":"path","required":true,"schema":{"type":"string","description":"LinkedIn account id (UUID).","title":"Linkedin Account Id"},"description":"LinkedIn account id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"team:delete","x-graph8-lifecycle":"active"}},"/teams/{team_id}/campaigns":{"get":{"tags":["Teams"],"summary":"List Team Campaigns","description":"The campaigns this team runs.","operationId":"list_team_campaigns_teams__team_id__campaigns_get","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"post":{"tags":["Teams"],"summary":"Assign Campaign To Team","description":"Link a campaign to a team. It does not start or stop anything.","operationId":"assign_campaign_to_team_teams__team_id__campaigns_post","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssignTeamCampaignRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/teams/{team_id}/campaigns/{campaign_id}":{"delete":{"tags":["Teams"],"summary":"Unassign Campaign From Team","description":"Unlink a campaign from a team. The campaign itself is untouched.","operationId":"unassign_campaign_from_team_teams__team_id__campaigns__campaign_id__delete","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id (UUID).","title":"Campaign Id"},"description":"Campaign id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"team:delete","x-graph8-lifecycle":"active"}},"/teams/{team_id}/sequences":{"get":{"tags":["Teams"],"summary":"List Team Sequences","description":"The sequences this team runs.","operationId":"list_team_sequences_teams__team_id__sequences_get","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/teams/{team_id}/chatbots":{"get":{"tags":["Teams"],"summary":"List Team Chatbots","description":"The web chatbots routed to this team.","operationId":"list_team_chatbots_teams__team_id__chatbots_get","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/newsletters/templates/layout":{"post":{"tags":["Newsletter"],"summary":"Create Template From Layout","description":"Build a template from a named layout archetype. ASYNC and AI-backed.\n\n202 rather than 201: the row exists immediately but the copy inside it is\nstill being generated. Poll\n`GET /newsletters/templates/{template_id}/generation-status` - a template\nread before that reports done is a half-written one.","operationId":"create_template_from_layout_newsletters_templates_layout_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TemplateFromLayoutRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/templates/custom":{"post":{"tags":["Newsletter"],"summary":"Create Template From Prompt","description":"Build a template from a plain-language idea. ASYNC and AI-backed.\n\n`voice_reference_issue_ids` points the model at past issues to imitate,\nwhich is the difference between generic copy and something that sounds like\nthe organisation. Same polling contract as `/templates/layout`.","operationId":"create_template_from_prompt_newsletters_templates_custom_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TemplateFromPromptRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/templates/clone":{"post":{"tags":["Newsletter"],"summary":"Clone Template","description":"Import an existing email as a template.\n\n`source` decides which of `url`, `issue_id` and `html` is read - the other\ntwo are ignored rather than rejected, so sending all three is not an error\nand not a merge.","operationId":"clone_template_newsletters_templates_clone_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TemplateCloneRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/templates/generation-status":{"post":{"tags":["Newsletter"],"summary":"Batch Template Generation Status","description":"Poll many template builds at once.\n\nA POST because the id list is the request, not a filter. Capped at 200 ids\n- the cap is the app's, and it exists because this is polled every couple\nof seconds.","operationId":"batch_template_generation_status_newsletters_templates_generation_status_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TemplateGenerationStatusBatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"}},"/newsletters/templates/{template_id}/generation-status":{"get":{"tags":["Newsletter"],"summary":"Template Generation Status","description":"How far along one template build is.\n\nDurable, not in-memory: a poll that arrives after a worker restart still\ngets the truth rather than a reset.","operationId":"template_generation_status_newsletters_templates__template_id__generation_status_get","parameters":[{"name":"template_id","in":"path","required":true,"schema":{"type":"integer","description":"Template id.","title":"Template Id"},"description":"Template id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"}},"/newsletters/templates/{template_id}/use":{"post":{"tags":["Newsletter"],"summary":"Use Template","description":"Turn a template into a new DRAFT issue on a newsletter.\n\nA copy, not a link: editing the issue afterwards leaves the template alone,\nand editing the template does not reach back into issues already made from\nit.","operationId":"use_template_newsletters_templates__template_id__use_post","parameters":[{"name":"template_id","in":"path","required":true,"schema":{"type":"integer","description":"Template id.","title":"Template Id"},"description":"Template id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UseTemplateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"}},"/newsletters/templates/{template_id}/approval":{"post":{"tags":["Newsletter"],"summary":"Set Template Approval","description":"Move a template through its lifecycle.\n\n`approved` is what makes it usable in the gallery; `archived` takes it out\nof circulation without destroying it. One explicit status rather than\nseparate approve and reject calls, so a retry is idempotent instead of\ntoggling.","operationId":"set_template_approval_newsletters_templates__template_id__approval_post","parameters":[{"name":"template_id","in":"path","required":true,"schema":{"type":"integer","description":"Template id.","title":"Template Id"},"description":"Template id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetTemplateApprovalRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"}},"/newsletters/templates/{template_id}/set-button-action":{"post":{"tags":["Newsletter"],"summary":"Set Template Button Action","description":"Repoint a button in a template. Deterministic - no AI, no credit.","operationId":"set_template_button_action_newsletters_templates__template_id__set_button_action_post","parameters":[{"name":"template_id","in":"path","required":true,"schema":{"type":"integer","description":"Template id.","title":"Template Id"},"description":"Template id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetButtonActionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"}},"/newsletters/templates/{template_id}/set-media-edit":{"post":{"tags":["Newsletter"],"summary":"Set Template Media Edit","description":"Change or remove an image in a template. Deterministic - no AI.","operationId":"set_template_media_edit_newsletters_templates__template_id__set_media_edit_post","parameters":[{"name":"template_id","in":"path","required":true,"schema":{"type":"integer","description":"Template id.","title":"Template Id"},"description":"Template id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetMediaEditRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}":{"patch":{"tags":["Newsletter"],"summary":"Update Newsletter","description":"Rename a newsletter, restate its goal, or repoint its audience.\n\nRepointing the audience changes where NEW subscribers come from. It does\nnot move, remove or re-import anybody already subscribed.","operationId":"update_newsletter_newsletters__newsletter_id__patch","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateNewsletterRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"},"get":{"tags":["Newsletter"],"summary":"Get Newsletter","description":"Get a single newsletter.","operationId":"get_newsletter_newsletters__newsletter_id__get","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter UUID","title":"Newsletter Id"},"description":"Newsletter UUID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/activate":{"post":{"tags":["Newsletter"],"summary":"Activate Newsletter","description":"Take a draft newsletter live. LAUNCH-CLASS.\n\nOnce active, the scheduler will send any issue whose scheduled time has\npassed - so this is not a metadata change, it is the switch that lets mail\nleave the building. Gated on `campaigns:launch`, the same permission the\nin-app route requires.","operationId":"activate_newsletter_newsletters__newsletter_id__activate_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/resume":{"post":{"tags":["Newsletter"],"summary":"Resume Newsletter","description":"Un-pause a newsletter. LAUNCH-CLASS, and the counterpart to the\npublished `POST /newsletters/{id}/pause`.\n\nResuming alone can put mail in real inboxes: pausing reverts scheduled\nissues to draft, but nothing prevents an issue being scheduled while the\nnewsletter is paused, and the scheduler's due-issue query filters on the\nNEWSLETTER's status. Gated on `campaigns:launch` for that reason.","operationId":"resume_newsletter_newsletters__newsletter_id__resume_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/settings":{"get":{"tags":["Newsletter"],"summary":"Get Newsletter Settings","description":"Who this newsletter sends as, and whether double opt-in is active.","operationId":"get_newsletter_settings_newsletters__newsletter_id__settings_get","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"},"put":{"tags":["Newsletter"],"summary":"Update Newsletter Settings","description":"Set the sender identity and the opt-in policy.\n\nSet `double_opt_in_intent` rather than `double_opt_in`: the active flag the\nsend pipeline reads is promoted automatically once the domain is verified\nand a sender address exists, and writing the active flag directly asks for\na state the pipeline is not ready for.","operationId":"update_newsletter_settings_newsletters__newsletter_id__settings_put","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateNewsletterSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/settings/verify-domain":{"post":{"tags":["Newsletter"],"summary":"Verify Newsletter Domain","description":"Start verification of a sending domain and get the DNS records back.\n\nThe records include DMARC, which Gmail and Yahoo require of bulk senders -\npublishing SPF and DKIM alone will pass this check and still land in spam.\nDomains bought through graph8 have their DNS added automatically; for a\ndomain you own, the records have to be added at your own provider.","operationId":"verify_newsletter_domain_newsletters__newsletter_id__settings_verify_domain_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VerifyDomainRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/settings/domain-status":{"get":{"tags":["Newsletter"],"summary":"Newsletter Domain Status","description":"Whether the sending domain and its DKIM keys have verified yet.\n\nPoll this after adding the DNS records. It is not a passive read: when the\nprovider reports the domain verified, this call is what promotes it into\nthe sender picker.","operationId":"newsletter_domain_status_newsletters__newsletter_id__settings_domain_status_get","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"domain","in":"query","required":true,"schema":{"type":"string","description":"The domain to check.","title":"Domain"},"description":"The domain to check."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/subscribers/import-audience":{"post":{"tags":["Newsletter"],"summary":"Import Subscribers From Audience","description":"Bulk-import an audience list's contacts as subscribers.\n\nAsynchronous: the response acknowledges the job rather than reporting a\nfinal count. Whether the imported addresses are verified on the way in\ndepends on `auto_verify_on_import` in the newsletter's settings, and\nverification SPENDS CREDIT.","operationId":"import_subscribers_from_audience_newsletters__newsletter_id__subscribers_import_audience_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ImportAudienceRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/subscribers/{subscriber_id}":{"delete":{"tags":["Newsletter"],"summary":"Delete Subscriber","description":"Remove a subscriber outright.\n\nDIFFERENT from `PATCH .../subscribers/{id}/unsubscribe`, which keeps the\nrow and records that they opted out. Deleting loses that record, so the\nsame address can be re-imported and mailed again - which is usually not\nwhat a person who unsubscribed wanted. Unsubscribe unless you are erasing\nsomeone on request.","operationId":"delete_subscriber_newsletters__newsletter_id__subscribers__subscriber_id__delete","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"subscriber_id","in":"path","required":true,"schema":{"type":"integer","description":"Subscriber id.","title":"Subscriber Id"},"description":"Subscriber id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"newsletter:delete","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}":{"delete":{"tags":["Newsletter"],"summary":"Delete Issue","description":"Delete a DRAFT issue.\n\nDrafts only - an issue that has been sent is a record of mail real people\nreceived and the app refuses to remove it.","operationId":"delete_issue_newsletters__newsletter_id__issues__issue_id__delete","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id.","title":"Issue Id"},"description":"Issue id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"newsletter:delete","x-graph8-lifecycle":"active"},"get":{"tags":["Newsletter"],"summary":"Get Issue","description":"Get a single newsletter issue with stats.","operationId":"get_issue_newsletters__newsletter_id__issues__issue_id__get","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter UUID","title":"Newsletter Id"},"description":"Newsletter UUID"},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id","title":"Issue Id"},"description":"Issue id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IssueDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"},"put":{"tags":["Newsletter"],"summary":"Update Issue","description":"Update a draft issue in place. Only fields sent are changed. Rejects\nwith 400 for issues no longer in a draft-editable state (mirrors the\ninternal handler's own ValueError -> 400 mapping).","operationId":"update_issue_newsletters__newsletter_id__issues__issue_id__put","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter UUID","title":"Newsletter Id"},"description":"Newsletter UUID"},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id","title":"Issue Id"},"description":"Issue id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/IssueUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IssueDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/generation-status":{"get":{"tags":["Newsletter"],"summary":"Get Issue Generation Status","description":"How far along an issue's AI generation is.\n\nRead this before sending a generated issue: an issue whose generation has\nnot finished has partial HTML, and sending it mails the partial version.","operationId":"get_issue_generation_status_newsletters__newsletter_id__issues__issue_id__generation_status_get","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id.","title":"Issue Id"},"description":"Issue id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/set-text":{"post":{"tags":["Newsletter"],"summary":"Set Issue Text","description":"Replace one element's text, exactly as given. No AI and no credit.\n\n`element_id` is the `g8` id in the issue's rendered HTML, which is what\nmakes this addressable at all - it edits a named element rather than\nre-writing the document.","operationId":"set_issue_text_newsletters__newsletter_id__issues__issue_id__set_text_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id.","title":"Issue Id"},"description":"Issue id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetTextRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/set-button-action":{"post":{"tags":["Newsletter"],"summary":"Set Issue Button Action","description":"Repoint a button in an issue. Deterministic - no AI, no credit.","operationId":"set_issue_button_action_newsletters__newsletter_id__issues__issue_id__set_button_action_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id.","title":"Issue Id"},"description":"Issue id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetButtonActionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/set-media-edit":{"post":{"tags":["Newsletter"],"summary":"Set Issue Media Edit","description":"Change or remove an image in an issue. Deterministic - no AI.","operationId":"set_issue_media_edit_newsletters__newsletter_id__issues__issue_id__set_media_edit_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id.","title":"Issue Id"},"description":"Issue id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetMediaEditRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/rewrite-text":{"post":{"tags":["Newsletter"],"summary":"Rewrite Issue Text","description":"Rewrite one element with an AI instruction. THIS SPENDS AI CREDIT.\n\nThe deliberate counterpart to `set-text`: same target, but the model\ndecides the wording. Use `set-text` when you already know what it should\nsay - it is free, deterministic and cannot surprise you.","operationId":"rewrite_issue_text_newsletters__newsletter_id__issues__issue_id__rewrite_text_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id.","title":"Issue Id"},"description":"Issue id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RewriteTextRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/analytics/subscribers/{subscriber_id}/timeline":{"get":{"tags":["Newsletter"],"summary":"Get Subscriber Timeline","description":"One subscriber's whole story for one issue: delivered, opened, clicked,\nbounced, complained, and when.\n\nThe published KPI read gives the totals; this answers \"what happened to\nTHIS person\", which is what a support question actually needs.","operationId":"get_subscriber_timeline_newsletters__newsletter_id__issues__issue_id__analytics_subscribers__subscriber_id__timeline_get","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id.","title":"Issue Id"},"description":"Issue id."},{"name":"subscriber_id","in":"path","required":true,"schema":{"type":"integer","description":"Subscriber id.","title":"Subscriber Id"},"description":"Subscriber id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/send":{"get":{"tags":["Newsletter"],"summary":"Get Send Status","description":"Where an in-flight send has got to.\n\nGET on the same path the published POST starts a send on. `{\"active\": false}`\nmeans nothing is running - which is also what you get after a send has\nfinished, so this is a progress read rather than a history one.","operationId":"get_send_status_newsletters__newsletter_id__issues__issue_id__send_get","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id.","title":"Issue Id"},"description":"Issue id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"},"post":{"tags":["Newsletter"],"summary":"Send Issue","description":"Enqueue or schedule a newsletter issue for sending.\n\n202 Accepted: the request is validated and handed to the send worker\n(or persisted as scheduled) — actual SES delivery happens\nasynchronously. Poll ``g8_newsletter_get_issue`` to observe completion.\n``scheduled_at`` omitted/null sends immediately; a malformed\n``scheduled_at`` string returns 422 (not 500).","operationId":"send_issue_newsletters__newsletter_id__issues__issue_id__send_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter UUID","title":"Newsletter Id"},"description":"Newsletter UUID"},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id","title":"Issue Id"},"description":"Issue id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/IssueSendRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/send/pause":{"post":{"tags":["Newsletter"],"summary":"Pause Send","description":"Ask a running send to stop. The stop button.\n\nA REQUEST, not an instant state: recipients already leased by a worker are\nstill delivered, and the reported state stays `pausing` until the\nreconciler confirms it settled. It does not lie about that, so poll\n`GET .../send` rather than assuming.\n\nDeliberately NOT gated on the launch permission. Requiring a launch right\nto STOP a send would invert the safety model, and the app leaves it open\nfor that reason.","operationId":"pause_send_newsletters__newsletter_id__issues__issue_id__send_pause_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id.","title":"Issue Id"},"description":"Issue id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SendControlRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/send/resume":{"post":{"tags":["Newsletter"],"summary":"Resume Send","description":"Restart a paused send. LAUNCH-CLASS.\n\nThis is the one send control that starts delivery again, which is why it\ncarries the `campaigns:launch` gate its two neighbours do not.","operationId":"resume_send_newsletters__newsletter_id__issues__issue_id__send_resume_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id.","title":"Issue Id"},"description":"Issue id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/send/cancel":{"post":{"tags":["Newsletter"],"summary":"Cancel Send","description":"Abandon a send for good.\n\nUnlike pause, there is no resuming from here: whoever has already received\nthe issue has received it, and nobody else will. Ungated for the same\nreason pause is.","operationId":"cancel_send_newsletters__newsletter_id__issues__issue_id__send_cancel_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id (UUID).","title":"Newsletter Id"},"description":"Newsletter id (UUID)."},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id.","title":"Issue Id"},"description":"Issue id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SendControlRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"}},"/newsletters":{"get":{"tags":["Newsletter"],"summary":"List Newsletters","description":"List all newsletters for the org.","operationId":"list_newsletters_newsletters_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"},"post":{"tags":["Newsletter"],"summary":"Create Newsletter","description":"Create a new newsletter (the parent container issues live under).","operationId":"create_newsletter_newsletters_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NewsletterCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/templates":{"get":{"tags":["Newsletter"],"summary":"List Templates","description":"List org-level newsletter templates (reusable HTML scaffolds).","operationId":"list_templates_newsletters_templates_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues":{"get":{"tags":["Newsletter"],"summary":"List Issues","description":"List all issues for a newsletter.","operationId":"list_issues_newsletters__newsletter_id__issues_get","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter UUID","title":"Newsletter Id"},"description":"Newsletter UUID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"},"post":{"tags":["Newsletter"],"summary":"Create Issue","description":"Create a draft newsletter issue.","operationId":"create_issue_newsletters__newsletter_id__issues_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter UUID","title":"Newsletter Id"},"description":"Newsletter UUID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/IssueCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IssueDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/duplicate":{"post":{"tags":["Newsletter"],"summary":"Duplicate Issue","description":"Duplicate any issue as a new draft.","operationId":"duplicate_issue_newsletters__newsletter_id__issues__issue_id__duplicate_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter UUID","title":"Newsletter Id"},"description":"Newsletter UUID"},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Source issue id (any status)","title":"Issue Id"},"description":"Source issue id (any status)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IssueDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/unschedule":{"post":{"tags":["Newsletter"],"summary":"Unschedule Issue","description":"Move a SCHEDULED issue back to draft so the scheduler never dispatches it. Sends nothing.\n\nThe counterpart of `send` with a `scheduled_at`. Same launch gate and newsletter binding as `send`. 404 if the issue is\nnot in this organisation or this newsletter; 409 if it is not `scheduled` (for example the scheduler has already started\nsending it: from there it cannot be recalled).","operationId":"unschedule_issue_newsletters__newsletter_id__issues__issue_id__unschedule_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter UUID","title":"Newsletter Id"},"description":"Newsletter UUID"},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id","title":"Issue Id"},"description":"Issue id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/send-test":{"post":{"tags":["Newsletter"],"summary":"Send Test Email","description":"Send a test email for a newsletter issue to a single address.","operationId":"send_test_email_newsletters__newsletter_id__issues__issue_id__send_test_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter UUID","title":"Newsletter Id"},"description":"Newsletter UUID"},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id","title":"Issue Id"},"description":"Issue id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/IssueSendTestRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/subscribers":{"get":{"tags":["Newsletter"],"summary":"List Subscribers","description":"Paginated subscriber list for a newsletter.","operationId":"list_subscribers_newsletters__newsletter_id__subscribers_get","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter UUID","title":"Newsletter Id"},"description":"Newsletter UUID"},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":25,"title":"Page Size"}},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Free-text search over email/name","title":"Search"},"description":"Free-text search over email/name"},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated status filter (e.g. 'subscribed,bounced')","title":"Status"},"description":"Comma-separated status filter (e.g. 'subscribed,bounced')"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SubscriberListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"},"post":{"tags":["Newsletter"],"summary":"Add Subscriber","description":"Add a single subscriber (staff action, status=subscribed). Also\ncreates/links a first-class CRM contact so the subscriber joins the\ncentral suppression model (mirrors the manual public subscribe form).","operationId":"add_subscriber_newsletters__newsletter_id__subscribers_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter UUID","title":"Newsletter Id"},"description":"Newsletter UUID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SubscriberAddRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SubscriberSummary_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/subscribers/{subscriber_id}/unsubscribe":{"patch":{"tags":["Newsletter"],"summary":"Unsubscribe Subscriber","description":"Soft-unsubscribe a subscriber (sets status, preserves the row —\ndoes NOT hard-delete).","operationId":"unsubscribe_subscriber_newsletters__newsletter_id__subscribers__subscriber_id__unsubscribe_patch","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter UUID","title":"Newsletter Id"},"description":"Newsletter UUID"},{"name":"subscriber_id","in":"path","required":true,"schema":{"type":"integer","description":"Subscriber id","title":"Subscriber Id"},"description":"Subscriber id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/analytics/kpis":{"get":{"tags":["Newsletter"],"summary":"Get Issue Analytics Kpis","description":"Bucketed KPI counters for a sent issue (opens, clicks, bounces, ...).\n\nHonors the stale-flag pattern: a backend read failure returns HTTP 200\nwith ``stale=true`` and an empty ``kpis`` bucket rather than a 500, so\ncallers can distinguish \"genuinely zero engagement yet\" from \"read\nfailed\" without a try/except.","operationId":"get_issue_analytics_kpis_newsletters__newsletter_id__issues__issue_id__analytics_kpis_get","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter UUID","title":"Newsletter Id"},"description":"Newsletter UUID"},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id","title":"Issue Id"},"description":"Issue id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IssueAnalyticsKpis_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/pause":{"post":{"tags":["Newsletter"],"summary":"Pause Newsletter","description":"Pause a running newsletter. Stops further sends; the newsletter and its\nissues are untouched and it can be resumed in the app.","operationId":"pause_newsletter_newsletters__newsletter_id__pause_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id.","title":"Newsletter Id"},"description":"Newsletter id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterStatusResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/complete":{"post":{"tags":["Newsletter"],"summary":"Complete Newsletter","description":"Mark a newsletter completed. Terminal - it stops sending for good.\n\nThe internal handler validates the transition, so an illegal move from the\ncurrent status is refused there rather than silently applied.","operationId":"complete_newsletter_newsletters__newsletter_id__complete_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id.","title":"Newsletter Id"},"description":"Newsletter id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterStatusResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/list-syncs":{"get":{"tags":["Newsletter"],"summary":"List Newsletter List Syncs","description":"Audience lists feeding this newsletter's subscribers.","operationId":"list_newsletter_list_syncs_newsletters__newsletter_id__list_syncs_get","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id.","title":"Newsletter Id"},"description":"Newsletter id."},{"name":"audience_list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Resolve a CANDIDATE list that has no saved row yet. Returns a synthetic disabled entry carrying the live name and count, so a rebuilt enable dialog can state the number the worker will actually act on rather than a stale one.","title":"Audience List Id"},"description":"Resolve a CANDIDATE list that has no saved row yet. Returns a synthetic disabled entry carrying the live name and count, so a rebuilt enable dialog can state the number the worker will actually act on rather than a stale one."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ListSyncListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"},"post":{"tags":["Newsletter"],"summary":"Enable Newsletter List Sync","description":"Attach an audience list, and run the first sync inline.\n\n`attested_text` is stored VERBATIM: it is the consent wording the operator\nsaw when they asserted these people opted in, kept so the trail survives\nfuture copy edits. Pass the exact text your UI showed - not a summary.","operationId":"enable_newsletter_list_sync_newsletters__newsletter_id__list_syncs_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id.","title":"Newsletter Id"},"description":"Newsletter id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ListSyncEnableRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Any_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/list-syncs/{audience_list_id}":{"delete":{"tags":["Newsletter"],"summary":"Disable Newsletter List Sync","description":"Detach an audience list. Subscribers already added are NOT removed -\nthis stops future syncs, it does not unsubscribe anyone.","operationId":"disable_newsletter_list_sync_newsletters__newsletter_id__list_syncs__audience_list_id__delete","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id.","title":"Newsletter Id"},"description":"Newsletter id."},{"name":"audience_list_id","in":"path","required":true,"schema":{"type":"integer","description":"Audience list id.","title":"Audience List Id"},"description":"Audience list id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Any_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"newsletter:delete","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/list-syncs/{audience_list_id}/run":{"post":{"tags":["Newsletter"],"summary":"Run Newsletter List Sync","description":"Re-run a sync now rather than waiting for the worker.\n\nIdempotent in effect: it reconciles the list into the subscriber base, so\nrunning it twice adds nobody twice.","operationId":"run_newsletter_list_sync_newsletters__newsletter_id__list_syncs__audience_list_id__run_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id.","title":"Newsletter Id"},"description":"Newsletter id."},{"name":"audience_list_id","in":"path","required":true,"schema":{"type":"integer","description":"Audience list id.","title":"Audience List Id"},"description":"Audience list id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Any_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"}},"/signatures/settings":{"get":{"tags":["Signatures"],"summary":"Get Signature Settings","description":"Read the org-wide signature policy and its current version.\n\n``mode`` is ``off`` (nothing managed), ``default`` (managed, employees may\noverride) or ``enforced`` (managed, overrides refused).","operationId":"get_signature_settings_signatures_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SignatureSettingsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"signatures:read","x-graph8-lifecycle":"active"},"put":{"tags":["Signatures"],"summary":"Update Signature Settings","description":"Replace the signature policy.\n\nEnabling management requires a default template; ``enforced`` additionally\nrequires every active mailbox to already have an assignment. Send the\n``version`` you read — a concurrent change answers 409.","operationId":"update_signature_settings_signatures_settings_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignatureSettingsWrite"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SignatureSettingsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"signatures:write","x-graph8-lifecycle":"active"}},"/signatures/templates":{"get":{"tags":["Signatures"],"summary":"List Signature Templates","description":"List every non-archived signature template in the org.","operationId":"list_signature_templates_signatures_templates_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_SignatureTemplateResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"signatures:read","x-graph8-lifecycle":"active"},"post":{"tags":["Signatures"],"summary":"Create Signature Template","description":"Create a signature template.\n\nThe block list is validated the way the in-app editor validates it: exactly\none required, locked identity block, at most one optional banner slot, unique\nblock ids. A rejected template answers 422 with the reason.","operationId":"create_signature_template_signatures_templates_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignatureTemplateWrite"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SignatureTemplateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"signatures:write","x-graph8-lifecycle":"active"}},"/signatures/templates/{template_id}":{"get":{"tags":["Signatures"],"summary":"Get Signature Template","description":"Read one template, including the ``version`` needed to update it.","operationId":"get_signature_template_signatures_templates__template_id__get","parameters":[{"name":"template_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Signature template id","title":"Template Id"},"description":"Signature template id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SignatureTemplateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"signatures:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Signatures"],"summary":"Update Signature Template","description":"Replace a template's content. Send the ``version`` you read.","operationId":"update_signature_template_signatures_templates__template_id__patch","parameters":[{"name":"template_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Signature template id","title":"Template Id"},"description":"Signature template id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignatureTemplateWrite"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SignatureTemplateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"signatures:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Signatures"],"summary":"Archive Signature Template","description":"Archive a template.\n\nRefused with 409 while the template is still the org default, a department\ndefault, or assigned to any mailbox — reassign those first. Archiving hides\nthe template from the library; already-installed signatures are untouched.","operationId":"archive_signature_template_signatures_templates__template_id__delete","parameters":[{"name":"template_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Signature template id","title":"Template Id"},"description":"Signature template id"},{"name":"version","in":"query","required":true,"schema":{"type":"integer","description":"Template version you last read. A mismatch is a 409.","title":"Version"},"description":"Template version you last read. A mismatch is a 409."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SignatureArchiveResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"signatures:delete","x-graph8-lifecycle":"active"}},"/signatures/templates/{template_id}/set-default":{"post":{"tags":["Signatures"],"summary":"Set Default Signature Template","description":"Make this template the organisation default.\n\n``version`` is the POLICY version (from ``GET /signatures/settings``), not the\ntemplate's — this writes the policy document.","operationId":"set_default_signature_template_signatures_templates__template_id__set_default_post","parameters":[{"name":"template_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Signature template id","title":"Template Id"},"description":"Signature template id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignatureRevision"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SignatureVersionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"signatures:write","x-graph8-lifecycle":"active"}},"/signatures/templates/{template_id}/assign":{"post":{"tags":["Signatures"],"summary":"Assign Signature Template","description":"Point a set of mailboxes at this template and queue a re-install.\n\nTargets are mutually exclusive: explicit ``mailbox_ids``, every mailbox whose\nemployee is in ``department``, or ``all_mailboxes``. Every targeted mailbox\nmust already have an employee assignment (422 otherwise).","operationId":"assign_signature_template_signatures_templates__template_id__assign_post","parameters":[{"name":"template_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Signature template id","title":"Template Id"},"description":"Signature template id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignatureTemplateTargets"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SignatureBulkTemplateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"signatures:write","x-graph8-lifecycle":"active"}},"/signatures/templates/{template_id}/preview":{"post":{"tags":["Signatures"],"summary":"Preview Saved Signature Template","description":"Render a stored template. Reads only — nothing is saved or sent.\n\nSupply ``mailbox_id`` AND ``member_id`` to render with that employee's real\ndetails; omit them for sample data.","operationId":"preview_saved_signature_template_signatures_templates__template_id__preview_post","parameters":[{"name":"template_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Signature template id","title":"Template Id"},"description":"Signature template id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignatureSavedPreviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"signatures:write","x-graph8-lifecycle":"active"}},"/signatures/preview":{"post":{"tags":["Signatures"],"summary":"Preview Signature Template","description":"Render an unsaved template draft. Reads only — nothing is saved or sent.","operationId":"preview_signature_template_signatures_preview_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignaturePreviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"signatures:write","x-graph8-lifecycle":"active"}},"/signatures/members":{"get":{"tags":["Signatures"],"summary":"List Signature Members","description":"List the directory employees a mailbox signature can be assigned to.\n\n``id`` is the ``member_id`` required by ``POST /signatures/assignments``.","operationId":"list_signature_members_signatures_members_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_SignatureMember__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"signatures:read","x-graph8-lifecycle":"active"}},"/signatures/mailboxes":{"get":{"tags":["Signatures"],"summary":"List Signature Deployments","description":"List every mailbox's signature deployment: assignment, revision, status, drift.\n\n``revision`` here is the optimistic-concurrency token for every per-mailbox\nwrite below. ``alert`` is true when the deployment needs an admin — blocked,\nunassigned, missing a provider grant, drifted, or in restore conflict.","operationId":"list_signature_deployments_signatures_mailboxes_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"signatures:read","x-graph8-lifecycle":"active"}},"/signatures/assignments":{"post":{"tags":["Signatures"],"summary":"Assign Signature Identity","description":"Bind an employee identity to mailboxes and queue the first install.\n\nThis is a TAKEOVER: the mailbox's existing signature is captured for restore\nand replaced, which is why ``confirm_takeover`` must be ``true``. Every\nmailbox id must appear in ``expected_revisions`` (use ``0`` for a mailbox with\nno assignment yet) so a stale client cannot clobber a concurrent change.","operationId":"assign_signature_identity_signatures_assignments_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignatureAssignmentWrite"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_SignatureAssignmentResult__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"signatures:write","x-graph8-lifecycle":"active"}},"/signatures/mailboxes/push":{"post":{"tags":["Signatures"],"summary":"Push Signatures","description":"Queue a re-install for several mailboxes at once.\n\nEvery mailbox must have a live assignment; a restored or unassigned mailbox\nin the list fails the whole call with 422 rather than half-applying.","operationId":"push_signatures_signatures_mailboxes_push_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignatureBulkPushRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SignatureDeploymentStatus_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"signatures:write","x-graph8-lifecycle":"active"}},"/signatures/mailboxes/{mailbox_id}/push":{"post":{"tags":["Signatures"],"summary":"Push Signature","description":"Queue a re-compile and re-install for one mailbox.","operationId":"push_signature_signatures_mailboxes__mailbox_id__push_post","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","description":"Mailbox id (mailboxes.id) — from GET /signatures/mailboxes","title":"Mailbox Id"},"description":"Mailbox id (mailboxes.id) — from GET /signatures/mailboxes"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignatureRevision"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SignatureDeploymentStatus_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"signatures:write","x-graph8-lifecycle":"active"}},"/signatures/mailboxes/{mailbox_id}/restore":{"post":{"tags":["Signatures"],"summary":"Restore Signature","description":"Put back the signature this mailbox had before graph8 took it over.\n\nRefused with 409 while the policy is ``enforced``. If the installed content\nwas edited outside graph8 since takeover the deployment is parked as\n``restore_conflict`` and nothing is overwritten.","operationId":"restore_signature_signatures_mailboxes__mailbox_id__restore_post","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","description":"Mailbox id (mailboxes.id) — from GET /signatures/mailboxes","title":"Mailbox Id"},"description":"Mailbox id (mailboxes.id) — from GET /signatures/mailboxes"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignatureRevision"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SignatureDeploymentStatus_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"signatures:write","x-graph8-lifecycle":"active"}},"/signatures/mailboxes/{mailbox_id}/source":{"post":{"tags":["Signatures"],"summary":"Change Signature Source","description":"Choose what this mailbox sends: the org/department default, a named\ntemplate, or its own content.\n\n``custom`` performs the same restore as ``POST .../restore``.","operationId":"change_signature_source_signatures_mailboxes__mailbox_id__source_post","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","description":"Mailbox id (mailboxes.id) — from GET /signatures/mailboxes","title":"Mailbox Id"},"description":"Mailbox id (mailboxes.id) — from GET /signatures/mailboxes"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignatureSourceWrite"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SignatureDeploymentStatus_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"signatures:write","x-graph8-lifecycle":"active"}},"/signatures/setup-preview":{"post":{"tags":["Signatures"],"summary":"Preview Signature Setup","description":"Dry-run an assignment against the mail provider before committing it.\n\nConfirms the employee account and send-as alias resolve, and returns the\nsignature currently installed there. Write capability stays unverified until\na real deployment succeeds. A provider refusal answers 422 with the state and\nreason rather than a stack trace.","operationId":"preview_signature_setup_signatures_setup_preview_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignatureSetupPreviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"signatures:write","x-graph8-lifecycle":"active"}},"/signatures/campaigns":{"get":{"tags":["Signatures"],"summary":"List Signature Campaigns","description":"List signature banner campaigns and the ``revision`` needed to edit one.","operationId":"list_signature_campaigns_signatures_campaigns_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_SignatureCampaignResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"signatures:read","x-graph8-lifecycle":"active"},"post":{"tags":["Signatures"],"summary":"Create Signature Campaign","description":"Create a banner campaign.\n\nThe creative must be an OPTIONAL banner block, and ``starts_at`` /\n``ends_at`` must be timezone-aware with the end after the start. Campaigns\nstart in ``draft`` unless you set ``status``.","operationId":"create_signature_campaign_signatures_campaigns_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignatureCampaignWrite"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SignatureCampaignResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"signatures:write","x-graph8-lifecycle":"active"}},"/signatures/campaigns/preview":{"post":{"tags":["Signatures"],"summary":"Preview Signature Campaign","description":"Render a campaign banner and, optionally, test who it would reach.\n\nReads only. With ``mailbox_id`` set, ``matching`` explains whether the\ncampaign would apply to that sender and the supplied ``recipients``, and\nwhich campaign wins on priority.","operationId":"preview_signature_campaign_signatures_campaigns_preview_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignatureCampaignPreviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SignatureCampaignPreviewResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"signatures:write","x-graph8-lifecycle":"active"}},"/signatures/campaigns/{campaign_id}":{"patch":{"tags":["Signatures"],"summary":"Update Signature Campaign","description":"Replace a campaign's content or schedule. Send the ``revision`` you read.","operationId":"update_signature_campaign_signatures_campaigns__campaign_id__patch","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Signature campaign id","title":"Campaign Id"},"description":"Signature campaign id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SignatureCampaignWrite"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SignatureCampaignResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"signatures:write","x-graph8-lifecycle":"active"}},"/signatures/reports":{"get":{"tags":["Signatures"],"summary":"Get Signature Report","description":"Signature and campaign engagement: impressions and clicks by mailbox and campaign.","operationId":"get_signature_report_signatures_reports_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"signatures:read","x-graph8-lifecycle":"active"}},"/feedback/sending-domains/verify":{"post":{"tags":["Surveys"],"summary":"Verify Survey Domain","description":"Start verification of a domain for SURVEY sending, and get the DNS\nrecords back.\n\nThe records include DMARC, which Gmail and Yahoo require of bulk senders -\npublishing SPF and DKIM alone passes this check and still lands in spam.\n\nIdempotent: re-running it on a domain already being verified re-reads the\nrecords rather than starting again, and a previously FAILED domain is reset\nto pending so the reconciler picks it up.\n\nA domain bought through graph8 has its DNS added automatically; a domain\nyou own needs the records added at your own provider before\n`/status` will ever turn green.","operationId":"verify_survey_domain_feedback_sending_domains_verify_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VerifySurveyDomainRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SurveyDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"surveys:run","x-graph8-lifecycle":"active"}},"/feedback/sending-domains/status":{"get":{"tags":["Surveys"],"summary":"Survey Domain Status","description":"Whether the domain and its DKIM keys have verified yet.\n\nNot a passive read: when the provider reports the domain verified, THIS\ncall is what promotes it into `GET /feedback/sending-domains`. A caller\nthat never polls can end up with a domain that verified upstream and still\ndoes not appear in the picker.","operationId":"survey_domain_status_feedback_sending_domains_status_get","parameters":[{"name":"domain","in":"query","required":true,"schema":{"type":"string","description":"The domain to check.","title":"Domain"},"description":"The domain to check."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SurveyDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"surveys:read","x-graph8-lifecycle":"active"}},"/feedback/surveys":{"post":{"tags":["Surveys"],"summary":"Create Survey","description":"Create an NPS or CSAT survey.\n\n``type`` fixes the scale (NPS 0-10, CSAT 1-5 unless you override\n``scale_min`` / ``scale_max``). ``delivery_channel`` chooses email, the\nmessaging bridge, or the in-app widget. ``comment_mode`` controls whether a\nrespondent can add free text: ``none``, ``link`` (score click opens a form) or\n``html`` (textarea inside the email).","operationId":"create_survey_feedback_surveys_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateSurveyRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SurveyResponseDTO_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"surveys:write","x-graph8-lifecycle":"active"},"get":{"tags":["Surveys"],"summary":"List Surveys","description":"List every survey in the org, active and inactive.","operationId":"list_surveys_feedback_surveys_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_SurveyResponseDTO__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"surveys:read","x-graph8-lifecycle":"active"}},"/feedback/sending-domains":{"get":{"tags":["Surveys"],"summary":"List Survey Sending Domains","description":"Domains this org can send surveys from.\n\n``sender_email`` on a send or a trigger must belong to one of the\n``verified`` domains here. Unstamped domains are reconciled against the mail\nservice on the way through, so a domain verified out of band shows up without\nany extra call.","operationId":"list_survey_sending_domains_feedback_sending_domains_get","parameters":[{"name":"include_unverified","in":"query","required":false,"schema":{"type":"boolean","description":"Include domains that are pending or not set up, with their status.","default":false,"title":"Include Unverified"},"description":"Include domains that are pending or not set up, with their status."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_SurveySendingDomainDTO__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"surveys:read","x-graph8-lifecycle":"active"}},"/feedback/org-summary":{"get":{"tags":["Surveys"],"summary":"Get Survey Org Summary","description":"Org-wide NPS and CSAT: headline scores, response rates and per-survey rollups.","operationId":"get_survey_org_summary_feedback_org_summary_get","parameters":[{"name":"segment","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Restrict to one audience list id. Omit for all contacts.","title":"Segment"},"description":"Restrict to one audience list id. Omit for all contacts."},{"name":"bucket","in":"query","required":false,"schema":{"type":"string","description":"Trend bucket: day, week or month.","default":"week","title":"Bucket"},"description":"Trend bucket: day, week or month."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgSummaryDTO_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"surveys:read","x-graph8-lifecycle":"active"}},"/feedback/sends/{send_id}":{"get":{"tags":["Surveys"],"summary":"Get Survey Send","description":"Read one send's status and recipient count — the poll target after a send.","operationId":"get_survey_send_feedback_sends__send_id__get","parameters":[{"name":"send_id","in":"path","required":true,"schema":{"type":"integer","description":"Send id returned by POST /feedback/surveys/{survey_id}/send","title":"Send Id"},"description":"Send id returned by POST /feedback/surveys/{survey_id}/send"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SurveySendDTO_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"surveys:read","x-graph8-lifecycle":"active"}},"/feedback/companies/{company_id}/nps":{"get":{"tags":["Surveys"],"summary":"Get Company Survey Nps","description":"Account-level NPS: score, promoter/detractor split, coverage and per-contact rows.\n\nThe headline score is suppressed (null) below the minimum-respondent\nthreshold rather than published from a handful of answers. Contacts the\ncalling key cannot see are excluded from every figure, so the coverage\ndenominator matches the rows returned.","operationId":"get_company_survey_nps_feedback_companies__company_id__nps_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"Company id (mashup_companies.id)","title":"Company Id"},"description":"Company id (mashup_companies.id)"},{"name":"bucket","in":"query","required":false,"schema":{"type":"string","description":"Trend bucket: day, week or month.","default":"week","title":"Bucket"},"description":"Trend bucket: day, week or month."},{"name":"survey_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Restrict to one survey. Omit to combine every NPS survey.","title":"Survey Id"},"description":"Restrict to one survey. Omit to combine every NPS survey."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CompanyNpsDTO_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"surveys:read","x-graph8-lifecycle":"active"}},"/feedback/contacts/{contact_id}/history":{"get":{"tags":["Surveys"],"summary":"Get Contact Survey History","description":"Every survey answer this contact has given, newest first.\n\n``contact_id`` is the mashup_contacts PRIMARY KEY, which is what survey\nresponses are keyed on — not the ``CONTACT_ID`` business key.","operationId":"get_contact_survey_history_feedback_contacts__contact_id__history_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id (mashup_contacts.id — the primary key)","title":"Contact Id"},"description":"Contact id (mashup_contacts.id — the primary key)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContactHistoryDTO_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"surveys:read","x-graph8-lifecycle":"active"}},"/feedback/surveys/{survey_id}":{"get":{"tags":["Surveys"],"summary":"Get Survey","description":"Read one survey definition.","operationId":"get_survey_feedback_surveys__survey_id__get","parameters":[{"name":"survey_id","in":"path","required":true,"schema":{"type":"string","description":"Survey id (UUID) — from GET /feedback/surveys","title":"Survey Id"},"description":"Survey id (UUID) — from GET /feedback/surveys"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SurveyResponseDTO_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"surveys:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Surveys"],"summary":"Update Survey","description":"Update a survey. Only supplied fields change.\n\nSetting ``is_active: false`` stops new sends and in-app impressions while\nkeeping every response already collected.","operationId":"update_survey_feedback_surveys__survey_id__patch","parameters":[{"name":"survey_id","in":"path","required":true,"schema":{"type":"string","description":"Survey id (UUID) — from GET /feedback/surveys","title":"Survey Id"},"description":"Survey id (UUID) — from GET /feedback/surveys"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateSurveyRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SurveyResponseDTO_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"surveys:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Surveys"],"summary":"Delete Survey","description":"Delete a survey. Deactivate instead (``PATCH is_active: false``) if you\nstill need its responses for reporting.","operationId":"delete_survey_feedback_surveys__survey_id__delete","parameters":[{"name":"survey_id","in":"path","required":true,"schema":{"type":"string","description":"Survey id (UUID) — from GET /feedback/surveys","title":"Survey Id"},"description":"Survey id (UUID) — from GET /feedback/surveys"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SurveyDeleteResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"surveys:delete","x-graph8-lifecycle":"active"}},"/feedback/surveys/{survey_id}/send":{"post":{"tags":["Surveys"],"summary":"Send Survey","description":"Send a survey to an audience. Real mail goes to real people.\n\n``audience_ref`` is a list id. For the email channel ``sender_email`` must sit\non a verified sending domain (``GET /surveys/sending-domains``) and\n``subject`` is required. Set ``scheduled_at`` to queue it for later. Returns\n202 with a ``send_id`` — dispatch is asynchronous; poll\n``GET /surveys/sends/{send_id}``.","operationId":"send_survey_feedback_surveys__survey_id__send_post","parameters":[{"name":"survey_id","in":"path","required":true,"schema":{"type":"string","description":"Survey id (UUID) — from GET /feedback/surveys","title":"Survey Id"},"description":"Survey id (UUID) — from GET /feedback/surveys"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SendSurveyRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SurveySendAccepted_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"surveys:run","x-graph8-lifecycle":"active"}},"/feedback/surveys/{survey_id}/triggers":{"post":{"tags":["Surveys"],"summary":"Create Survey Trigger","description":"Bind an automated send to this survey.\n\n``scheduled`` needs ``audience_ref`` + ``cadence_days``; ``list_entry`` needs\n``audience_ref``; ``stage_entry`` needs ``stage_value``. An ``audience_ref``\nthat does not exist in this org is refused rather than silently never firing.","operationId":"create_survey_trigger_feedback_surveys__survey_id__triggers_post","parameters":[{"name":"survey_id","in":"path","required":true,"schema":{"type":"string","description":"Survey id (UUID) — from GET /feedback/surveys","title":"Survey Id"},"description":"Survey id (UUID) — from GET /feedback/surveys"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateSurveyTriggerRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SurveyTriggerDTO_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"surveys:write","x-graph8-lifecycle":"active"},"get":{"tags":["Surveys"],"summary":"List Survey Triggers","description":"List this survey's automated-send triggers.","operationId":"list_survey_triggers_feedback_surveys__survey_id__triggers_get","parameters":[{"name":"survey_id","in":"path","required":true,"schema":{"type":"string","description":"Survey id (UUID) — from GET /feedback/surveys","title":"Survey Id"},"description":"Survey id (UUID) — from GET /feedback/surveys"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_SurveyTriggerDTO__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"surveys:read","x-graph8-lifecycle":"active"}},"/feedback/surveys/{survey_id}/triggers/{trigger_id}":{"delete":{"tags":["Surveys"],"summary":"Delete Survey Trigger","description":"Remove an automated-send trigger. Scoped to its parent survey.","operationId":"delete_survey_trigger_feedback_surveys__survey_id__triggers__trigger_id__delete","parameters":[{"name":"survey_id","in":"path","required":true,"schema":{"type":"string","description":"Survey id (UUID) — from GET /feedback/surveys","title":"Survey Id"},"description":"Survey id (UUID) — from GET /feedback/surveys"},{"name":"trigger_id","in":"path","required":true,"schema":{"type":"string","description":"Trigger id — from GET /feedback/surveys/{survey_id}/triggers","title":"Trigger Id"},"description":"Trigger id — from GET /feedback/surveys/{survey_id}/triggers"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SurveyTriggerDeleteResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"surveys:delete","x-graph8-lifecycle":"active"}},"/feedback/surveys/{survey_id}/summary":{"get":{"tags":["Surveys"],"summary":"Get Survey Summary","description":"Headline score, response rate and distribution for one survey.","operationId":"get_survey_summary_feedback_surveys__survey_id__summary_get","parameters":[{"name":"survey_id","in":"path","required":true,"schema":{"type":"string","description":"Survey id (UUID) — from GET /feedback/surveys","title":"Survey Id"},"description":"Survey id (UUID) — from GET /feedback/surveys"},{"name":"bucket","in":"query","required":false,"schema":{"type":"string","description":"Trend bucket: day, week or month.","default":"week","title":"Bucket"},"description":"Trend bucket: day, week or month."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SummaryDTO_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"surveys:read","x-graph8-lifecycle":"active"}},"/feedback/surveys/{survey_id}/trends":{"get":{"tags":["Surveys"],"summary":"Get Survey Trends","description":"Score over time, bucketed by day, week or month.","operationId":"get_survey_trends_feedback_surveys__survey_id__trends_get","parameters":[{"name":"survey_id","in":"path","required":true,"schema":{"type":"string","description":"Survey id (UUID) — from GET /feedback/surveys","title":"Survey Id"},"description":"Survey id (UUID) — from GET /feedback/surveys"},{"name":"bucket","in":"query","required":false,"schema":{"type":"string","description":"Trend bucket: day, week or month.","default":"week","title":"Bucket"},"description":"Trend bucket: day, week or month."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_TrendsDTO_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"surveys:read","x-graph8-lifecycle":"active"}},"/feedback/surveys/{survey_id}/responses":{"get":{"tags":["Surveys"],"summary":"Get Survey Responses","description":"Individual contact responses: score, comment, contact and timestamp.","operationId":"get_survey_responses_feedback_surveys__survey_id__responses_get","parameters":[{"name":"survey_id","in":"path","required":true,"schema":{"type":"string","description":"Survey id (UUID) — from GET /feedback/surveys","title":"Survey Id"},"description":"Survey id (UUID) — from GET /feedback/surveys"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SurveyResponsesDTO_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"surveys:read","x-graph8-lifecycle":"active"}},"/feedback/surveys/{survey_id}/app-user-responses":{"get":{"tags":["Surveys"],"summary":"Get Survey App User Responses","description":"Responses collected from your own seat-holders via the in-app widget.\n\nKept separate from contact responses: these are colleagues answering inside\nthe product, not customers answering an email.","operationId":"get_survey_app_user_responses_feedback_surveys__survey_id__app_user_responses_get","parameters":[{"name":"survey_id","in":"path","required":true,"schema":{"type":"string","description":"Survey id (UUID) — from GET /feedback/surveys","title":"Survey Id"},"description":"Survey id (UUID) — from GET /feedback/surveys"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppUserResponsesDTO_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"surveys:read","x-graph8-lifecycle":"active"}},"/feedback/surveys/{survey_id}/sends":{"get":{"tags":["Surveys"],"summary":"Get Survey Sends","description":"Send history with per-send delivery breakdown and responder counts.","operationId":"get_survey_sends_feedback_surveys__survey_id__sends_get","parameters":[{"name":"survey_id","in":"path","required":true,"schema":{"type":"string","description":"Survey id (UUID) — from GET /feedback/surveys","title":"Survey Id"},"description":"Survey id (UUID) — from GET /feedback/surveys"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SurveySendsDTO_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"surveys:read","x-graph8-lifecycle":"active"}},"/support/contact":{"post":{"tags":["Support"],"summary":"Contact Support","description":"Send a message to graph8's human support team.\n\nThe reply channel is email: support answers to ``contact_email`` when\nprovided, otherwise to the authenticated user's own address.","operationId":"contact_support_support_contact_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContactSupportRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContactSupportResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/api-keys":{"get":{"tags":["API Keys"],"summary":"List Api Keys","description":"List every API key in the caller's own org (never the secret).","operationId":"list_api_keys_api_keys_get","parameters":[{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ApiKeyListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"post":{"tags":["API Keys"],"summary":"Create Api Key","description":"Mint a new API key for the caller's own org. The token is returned exactly once.","operationId":"create_api_key_api_keys_post","parameters":[{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiKeyCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ApiKeyCreateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/api-keys/scopes":{"get":{"tags":["API Keys"],"summary":"List Scope Catalog","description":"The scope vocabulary a key may be granted, so an automation can decide\nwhat to ask for without reading source. Read-only, org-independent.","operationId":"list_scope_catalog_api_keys_scopes_get","parameters":[{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ScopeCatalogResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/api-keys/{api_key_id}":{"delete":{"tags":["API Keys"],"summary":"Delete Api Key","description":"Revoke an API key. Idempotent: revoking a key that no longer exists\n(already revoked, or never existed in this org) returns 404, never 500.","operationId":"delete_api_key_api_keys__api_key_id__delete","parameters":[{"name":"api_key_id","in":"path","required":true,"schema":{"type":"string","title":"Api Key Id"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/api-keys/{api_key_id}/ip-allowlist":{"put":{"tags":["API Keys"],"summary":"Update Ip Allowlist","description":"Replace the IP allowlist for a key in-place. The token is unchanged.\n\nPass an empty list to remove all IP restrictions.\nGated by account:write (same as create/rotate/delete).","operationId":"update_ip_allowlist_api_keys__api_key_id__ip_allowlist_put","parameters":[{"name":"api_key_id","in":"path","required":true,"schema":{"type":"string","title":"Api Key Id"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiKeyIpAllowlistRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ApiKeyResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/api-keys/{api_key_id}/spending-limits":{"put":{"tags":["API Keys"],"summary":"Update Spending Limits","description":"Set the daily and monthly credit caps on a key. The token is unchanged.\n\nADMIN OR OWNER ONLY, and a key can NEVER change its own caps: a cap that the capped key could lift is not a cap.\nAn organization key additionally follows the rotation rules (a creator still in the organization, keys of the same\ncreator, scopes it holds). A full replace: `null` removes a window's cap. Billable calls past a cap are refused\nwith 402 until the window resets.","operationId":"update_spending_limits_api_keys__api_key_id__spending_limits_put","parameters":[{"name":"api_key_id","in":"path","required":true,"schema":{"type":"string","description":"Key id from GET /api-keys.","title":"Api Key Id"},"description":"Key id from GET /api-keys."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiKeySpendCapsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ApiKeyResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/api-keys/{api_key_id}/spending":{"get":{"tags":["API Keys"],"summary":"Get Key Spending","description":"A key's caps beside what it has spent today and this month (UTC).\n\nAn Admin or Owner reads any key of the organization; any other caller reads only the key it is using, which is how\na client throttles itself. Spend is best effort: if the counter store is down the caps are still returned with a\nspend of 0 rather than failing.","operationId":"get_key_spending_api_keys__api_key_id__spending_get","parameters":[{"name":"api_key_id","in":"path","required":true,"schema":{"type":"string","description":"Key id from GET /api-keys.","title":"Api Key Id"},"description":"Key id from GET /api-keys."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ApiKeySpendResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/api-keys/{api_key_id}/rotate":{"post":{"tags":["API Keys"],"summary":"Rotate Api Key","description":"Rotate a key, preserving its mode, scopes and agency status.\n\nThe old key is deleted and a policy-equivalent replacement is minted; the\nnew token is returned exactly once. Ownership is enforced by the org-scoped\nlookup below (mirroring the delete route) plus `rotate_api_key`'s own\norg-scoped read-back (`campaign_builder/services/propelauth.py`).\n\nGuard 4 (mode non-escalation) applies here too — see module docstring point\n4. Rotation PRESERVES the target key's mode, so without this a `test`-mode\ncaller could rotate a `live` key and receive a brand-new `live` token (while\ninvalidating the working live key). That is the same escalation the create\nroute coerces away, so refuse it here rather than coerce: a rotation cannot\nbe silently downgraded to `test` without destroying a working live key.","operationId":"rotate_api_key_api_keys__api_key_id__rotate_post","parameters":[{"name":"api_key_id","in":"path","required":true,"schema":{"type":"string","title":"Api Key Id"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiKeyRotateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ApiKeyCreateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/enrichment/lookup/person":{"post":{"tags":["Enrichment"],"summary":"Lookup Person","description":"Instant person lookup by email, LinkedIn URL, or name + company domain.","operationId":"lookup_person_enrichment_lookup_person_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonLookupRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LookupResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/person":{"post":{"tags":["Enrichment"],"summary":"Lookup Person (alias of /enrichment/lookup/person)","description":"Alias of `POST /enrichment/lookup/person`: same request body, response, scope (`enrichment:run`) and credit charge. Prefer the canonical path in new code.","operationId":"lookup_person_alias_enrichment_person_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonLookupRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LookupResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/lookup/company":{"post":{"tags":["Enrichment"],"summary":"Lookup Company","description":"Instant company lookup by domain or name.","operationId":"lookup_company_enrichment_lookup_company_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CompanyLookupRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LookupResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/enrich":{"post":{"tags":["Enrichment"],"summary":"Start Enrichment","description":"Start an async waterfall enrichment job. Returns a job_id to poll for results.","operationId":"start_enrichment_enrichment_enrich_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EnrichRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/jobs/{job_id}":{"get":{"tags":["Enrichment"],"summary":"Get Enrichment Job","description":"Poll the status of an enrichment job.\n\nResolution order:\n    1. Redis ``job_state_cache`` (sub-millisecond, written by the\n       waterfall worker pipeline).\n    2. ``enrichment_jobs`` table in the org schema (written by every\n       enrichment handler including AI). DB fallback covers two cases:\n       Redis cache eviction for old waterfall jobs, AND AI jobs whose\n       handler isn't wired to the cache (see ``AIEnrichmentHandler``).\n\nReturning DB-resolved jobs also populates ``total`` / ``completed``\ncounters that Redis-only resolutions leave as ``None`` - so callers\npolling AI jobs see progress without a separate detail call.","operationId":"get_enrichment_job_enrichment_jobs__job_id__get","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","title":"Job Id"}},{"name":"include_provider_errors","in":"query","required":false,"schema":{"type":"boolean","description":"When true, include per-provider step errors (record_id, provider, error) from the job records, e.g. '<provider> API key is not configured'. Adds one DB read; off by default.","default":false,"title":"Include Provider Errors"},"description":"When true, include per-provider step errors (record_id, provider, error) from the job records, e.g. '<provider> API key is not configured'. Adds one DB read; off by default."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/verify-email":{"post":{"tags":["Enrichment"],"summary":"Verify Email","description":"Verify a single email address and return its deliverability status.","operationId":"verify_email_enrichment_verify_email_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VerifyEmailRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VerifyEmailResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/waterfall/configs":{"get":{"tags":["Enrichment"],"summary":"List Waterfall Configs","description":"List active waterfall pipelines saved for a list.\n\nReturns configs where `list_id` matches OR `is_global=true`. The UI treats\nthese as the \"runnable pipelines for this list\" set. Each summary includes\nthe `column_id` clients need for `POST /enrichment/waterfall/enrich`.\n\nEmpty list means the caller should auto-create one (see\n`POST /enrichment/waterfall/configs`).","operationId":"list_waterfall_configs_enrichment_waterfall_configs_get","parameters":[{"name":"list_id","in":"query","required":true,"schema":{"type":"integer","description":"List ID whose saved pipelines to return","title":"List Id"},"description":"List ID whose saved pipelines to return"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WaterfallConfigsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"},"post":{"tags":["Enrichment"],"summary":"Create Default Waterfall Config","description":"Create (or reuse) a waterfall pipeline on a list.\n\nThree call-styles (mutually exclusive between `providers[]` and `steps[]`):\n\n* **Bare** — pass only `list_id`. Builds a single-step graph8 lookup.\n* **By providers** — pass `providers=[\"hunter\",\"prospeo\"]`. Builds default\n  email-finder steps in that order.\n* **By steps** — pass `steps=[...]` with full step shapes. Persisted\n  verbatim (matches the canonical `WaterfallStepDto` shape the UI saves).\n\n`email_verification` may be combined with any call-style.\n\nIdempotent by `(list_id, name)`: if a pipeline with the same name already\nexists on this list, returns its column_id with `created=False` instead\nof creating a duplicate. Mirrors the dedup behaviour of the UI's\n`POST /enrichments/waterfall/save` endpoint.","operationId":"create_default_waterfall_config_enrichment_waterfall_configs_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateDefaultWaterfallConfigRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CreateDefaultWaterfallConfigResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/providers":{"get":{"tags":["Enrichment"],"summary":"List Enrichment Providers","description":"List enrichment providers with their credential mode + credit cost.\n\nFor each provider: whether graph8 funds it with a system key (`system_funded`\n- usable with no setup but charges credits), whether the org has its own key\n(`byok_configured`), what `credential_mode='auto'` resolves to for this org\nright now (`default_credential_source`), and the per-action credit costs.\n\nThis is the programmatic equivalent of the UI's provider picker - call it\nbefore building a pipeline so you know which providers run on graph8's system\ncredentials by default and which require your own API key.","operationId":"list_enrichment_providers_enrichment_providers_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ProviderCatalogResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/waterfall/enrich":{"post":{"tags":["Enrichment"],"summary":"Run Waterfall Pipeline","description":"Run a saved waterfall pipeline on specific records.\n\nThe handler loads the pipeline's step list from the DB by `column_id`,\nwhich means providers that require credentials (Prospeo, Dropcontact, etc.)\nuse whichever resolution the pipeline was saved with — the org's own API\nkeys OR graph8-managed system keys. Credits are deducted only for steps\nthat actually run.","operationId":"run_waterfall_pipeline_enrichment_waterfall_enrich_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RunWaterfallEnrichRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/ai/configs":{"get":{"tags":["Enrichment"],"summary":"List Ai Configs","description":"List active AI enrichment configs runnable on a list.\n\nReturns configs where `list_id` matches OR `is_global=true`. Each\nsummary includes a `group_id` the caller passes back to\n`POST /enrichment/ai/enrich`. Empty list means the org has no AI\nconfigs and must create one in the UI before AI enrichment is usable.","operationId":"list_ai_configs_enrichment_ai_configs_get","parameters":[{"name":"list_id","in":"query","required":true,"schema":{"type":"integer","description":"List ID whose saved AI configs to return","title":"List Id"},"description":"List ID whose saved AI configs to return"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AIConfigsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"},"post":{"tags":["Enrichment"],"summary":"Save Ai Enrichment Config","description":"Create an AI enrichment group on a list. FREE - saving never runs.\n\nPLURAL, matching the `GET /enrichment/ai/configs` that already ships. The\napp spells this one `/ai/config`; publishing both would be two paths one\nletter apart.\n\n`config.is_global` true - the app's DEFAULT - makes the group apply to\nEVERY list in the organisation, not just `config.list_id`. That is the\nwider blast radius of the two and it is what you get by omission, so set it\ndeliberately.\n\nA `config.group_id` naming a qualification group shared by every list (the\nICP and Persona qualification groups) answers 409 with code\n`shared_qualification_group`: those groups cannot gain columns here.","operationId":"save_ai_enrichment_config_enrichment_ai_configs_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SaveAIConfigRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/enrichment/ai/enrich":{"post":{"tags":["Enrichment"],"summary":"Run Ai Enrichment","description":"Run a saved AI enrichment config (web-research / content-gen) on records.\n\nDelegates to ``AIEnrichmentHandler`` (the same handler the UI uses).\nUnlike the waterfall endpoint - which queues an async job - this call\nruns synchronously: ``handler.run()`` blocks until every record has\nbeen processed (typical: 30-120 s for a handful of contacts on the\nweb-research usecase). The response therefore returns ``status=\"completed\"``\nwith the final counters inline, not a queued job_id to poll.\n\nThe job_id is still returned for audit / cross-reference - polling it\nvia ``GET /jobs/{job_id}`` works thanks to the DB fallback on that\nendpoint, but most callers will get everything they need from this\nresponse directly.\n\nCredits are charged up-front at the web-research baseline\n(``CREDITS_AI_ENRICH_ESTIMATE``). The handler does not charge\nadditionally, so this is the only credit deduction per call.","operationId":"run_ai_enrichment_enrichment_ai_enrich_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RunAIEnrichRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/preflight":{"post":{"tags":["Enrichment"],"summary":"Preflight Enrichment","description":"Check an enrichment request before running it. Free: nothing is written,\nqueued or charged.\n\nErrors for input a run could never use: an unknown `mode` (400\n`invalid_mode`), zero or negative contact IDs (400 `invalid_record_ids`), a\nlist that is not in this organization (404 `list_not_found`), an unknown\n`target_field` (400 `unsupported_field`), an unknown provider (400\n`unsupported_provider` / `unsupported_provider_for_field`) and a missing AI\nconfig (404 `ai_config_not_found`).\n\nOtherwise returns what the run would do: the unique contact IDs (repeats\nare counted once), contacts that are not on the list, the providers that\nwould run, and plain warnings such as \"Lusha is not connected: add your\nkey\" or \"No providers chosen: using your saved pipeline\".","operationId":"preflight_enrichment_enrichment_preflight_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EnrichmentPreflightRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPreflightResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/envelopes":{"post":{"tags":["E-Signature"],"summary":"Create Envelope","description":"Create a DRAFT envelope. Nothing is emailed.\n\nThe documents are HTML the caller already holds - there is no upload step -\nwhich is what makes the whole flow scriptable. `expires_in_days` counts\nfrom creation, NOT from the moment it is sent, so a draft left sitting for\na month has already used its window.","operationId":"create_envelope_envelopes_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateEnvelopeRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnvelopePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"quotes:write","x-graph8-lifecycle":"active"},"get":{"tags":["E-Signature"],"summary":"List Envelopes","description":"Envelopes in the organisation, newest first.\n\n`source_type` + `source_id` is the join back to whatever produced the\nenvelope, so \"has the quote I sent been signed\" is one call rather than a\nscan.","operationId":"list_envelopes_envelopes_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"`draft`, `sent`, `viewed`, `completed`, `voided`, `expired`.","title":"Status"},"description":"`draft`, `sent`, `viewed`, `completed`, `voided`, `expired`."},{"name":"source_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"What produced the envelope, e.g. `quote`.","title":"Source Type"},"description":"What produced the envelope, e.g. `quote`."},{"name":"source_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"The producing record's id.","title":"Source Id"},"description":"The producing record's id."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnvelopeListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/envelopes/{envelope_id}":{"get":{"tags":["E-Signature"],"summary":"Get Envelope","description":"One envelope, with its documents and its full audit trail.\n\nThe audit trail is the answer to \"did they actually see it\": it records\nwhen the link was opened, not only when the signature landed.","operationId":"get_envelope_envelopes__envelope_id__get","parameters":[{"name":"envelope_id","in":"path","required":true,"schema":{"type":"string","description":"Envelope id (UUID).","title":"Envelope Id"},"description":"Envelope id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnvelopePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"},"delete":{"tags":["E-Signature"],"summary":"Delete Envelope","description":"Delete a DRAFT envelope.\n\nDrafts only: anything that has been sent comes back as a 400, because a\ndocument a person has already been asked to sign is evidence and is voided\nrather than removed. The delete is soft and the audit trail survives it.","operationId":"delete_envelope_envelopes__envelope_id__delete","parameters":[{"name":"envelope_id","in":"path","required":true,"schema":{"type":"string","description":"Envelope id (UUID).","title":"Envelope Id"},"description":"Envelope id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnvelopePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"quotes:delete","x-graph8-lifecycle":"active"}},"/envelopes/{envelope_id}/send":{"post":{"tags":["E-Signature"],"summary":"Send Envelope","description":"Send the envelope for signature. THIS EMAILS A REAL PERSON.\n\nNot a state change with a side effect - the side effect IS the point: the\nsigner gets a link that carries its own credential, and from that moment\nthe document is in front of somebody outside the organisation.\n\nTiered `external` rather than `write` for exactly that reason.","operationId":"send_envelope_envelopes__envelope_id__send_post","parameters":[{"name":"envelope_id","in":"path","required":true,"schema":{"type":"string","description":"Envelope id (UUID).","title":"Envelope Id"},"description":"Envelope id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SendEnvelopeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnvelopePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/envelopes/{envelope_id}/resend":{"post":{"tags":["E-Signature"],"summary":"Resend Envelope","description":"Email the signing link again. ALSO REACHES A REAL PERSON.\n\nOnly valid while the envelope is `sent` or `viewed` - a draft has never\nbeen sent and a completed one has nothing left to chase, and both come back\nas a 400 rather than silently doing nothing. The link itself is unchanged,\nso an earlier email still works.","operationId":"resend_envelope_envelopes__envelope_id__resend_post","parameters":[{"name":"envelope_id","in":"path","required":true,"schema":{"type":"string","description":"Envelope id (UUID).","title":"Envelope Id"},"description":"Envelope id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnvelopePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"quotes:run","x-graph8-lifecycle":"active"}},"/envelopes/{envelope_id}/void":{"post":{"tags":["E-Signature"],"summary":"Void Envelope","description":"Cancel an envelope that is already out.\n\nThe signing link stops working, so this is the operation to reach for when\na document was sent in error - deleting it is not, because a sent envelope\ncannot be deleted at all. The audit trail is preserved.","operationId":"void_envelope_envelopes__envelope_id__void_post","parameters":[{"name":"envelope_id","in":"path","required":true,"schema":{"type":"string","description":"Envelope id (UUID).","title":"Envelope Id"},"description":"Envelope id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnvelopePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"quotes:delete","x-graph8-lifecycle":"active"}},"/enrichment/generate-prompt":{"post":{"tags":["Enrichment"],"summary":"Generate Enrichment Prompt","description":"Write an enrichment prompt from a list's columns. COSTS AN AI CALL.\n\nA model reads the list's columns and sample rows and drafts a prompt for\nthe task you describe. The result is a draft - nothing is configured and no\nrecord is enriched until you save it.","operationId":"generate_enrichment_prompt_enrichment_generate_prompt_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PromptGeneratorRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/ai-formula/generate-condition":{"post":{"tags":["Enrichment"],"summary":"Generate Ai Run Condition","description":"Turn a rule in words into a run condition. SPENDS CREDITS, TOKEN-METERED.\n\n\"Only run for CEOs with no work email\" becomes an expression you can put in\na config's `run_condition`, so the enrichment skips rows it should not\ntouch - which is how this pays for itself.\n\nThe charge is METERED ON TOKENS rather than flat: a long rule with a large\nsample record costs more than a short one. Keep `sampleData` to a single\nrepresentative record.","operationId":"generate_ai_run_condition_enrichment_ai_formula_generate_condition_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AIRunConditionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/ai-formula/available-fields":{"get":{"tags":["Enrichment"],"summary":"List Ai Formula Available Fields","description":"The fields a formula or run condition may reference. FREE.\n\nThe vocabulary the generator above is allowed to use. Anything outside it\nwill not resolve at evaluation time.","operationId":"list_ai_formula_available_fields_enrichment_ai_formula_available_fields_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/waterfall/allowed-columns":{"get":{"tags":["Enrichment"],"summary":"List Waterfall Allowed Columns","description":"Columns a waterfall enrichment may write into on this list. FREE.","operationId":"list_waterfall_allowed_columns_enrichment_waterfall_allowed_columns_get","parameters":[{"name":"list_id","in":"query","required":true,"schema":{"type":"integer","description":"Which list's columns to report.","title":"List Id"},"description":"Which list's columns to report."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/ai/validate-credits":{"post":{"tags":["Enrichment"],"summary":"Validate Ai Enrichment Credits","description":"Price an AI enrichment before running it. CHARGES NOTHING.\n\nResolves how many records the scope covers, what the group's usecase costs\nper record, and whether the balance covers it. Call it first: this is the\nonly way to learn the price without paying it.\n\nThe scope fields mirror the run's exactly, so the same body prices what the\nrun would then do. A body that names no scope prices the whole list.","operationId":"validate_ai_enrichment_credits_enrichment_ai_validate_credits_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ValidateCreditsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/waterfall/validate-credits":{"post":{"tags":["Enrichment"],"summary":"Validate Waterfall Enrichment Credits","description":"Price a waterfall enrichment before running it. CHARGES NOTHING.\n\nA waterfall tries providers in order until one answers, so the price\ndepends on which providers the column is configured with. `credits_per_\nrecord` in the body is a deprecated field the server ignores - pricing is\ncomputed from the configuration, not from what the caller claims.","operationId":"validate_waterfall_enrichment_credits_enrichment_waterfall_validate_credits_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ValidateWaterfallCreditsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/ai/configs/{group_id}/rename":{"put":{"tags":["Enrichment"],"summary":"Rename Ai Enrichment Column","description":"Rename the column an AI group writes into. Free.\n\nDisplay name only - the underlying column id does not move, so formulas and\nmappings that reference it keep working. A qualification group shared by\nevery list answers 409 unless `scope=org` (admin keys only).","operationId":"rename_ai_enrichment_column_enrichment_ai_configs__group_id__rename_put","parameters":[{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"AI group id.","title":"Group Id"},"description":"AI group id."},{"name":"scope","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^org$"},{"type":"null"}],"description":"Set to `org` to change or delete a qualification group shared by every list (the ICP and Persona qualification groups). Admin keys only. Without it such a call answers 409 with code `shared_qualification_group`.","title":"Scope"},"description":"Set to `org` to change or delete a qualification group shared by every list (the ICP and Persona qualification groups). Admin keys only. Without it such a call answers 409 with code `shared_qualification_group`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RenameAIColumnRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/enrichment/ai/configs/{group_id}":{"delete":{"tags":["Enrichment"],"summary":"Delete Ai Config By Group","description":"Remove an AI group and every column it owns. Free.\n\nA qualification group shared by every list answers 409 unless `scope=org`\n(admin keys only).","operationId":"delete_ai_config_by_group_enrichment_ai_configs__group_id__delete","parameters":[{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"AI group id.","title":"Group Id"},"description":"AI group id."},{"name":"hard_delete","in":"query","required":false,"schema":{"type":"boolean","description":"Remove the configuration permanently instead of deactivating it. The values it already wrote are kept either way.","default":false,"title":"Hard Delete"},"description":"Remove the configuration permanently instead of deactivating it. The values it already wrote are kept either way."},{"name":"scope","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^org$"},{"type":"null"}],"description":"Set to `org` to change or delete a qualification group shared by every list (the ICP and Persona qualification groups). Admin keys only. Without it such a call answers 409 with code `shared_qualification_group`.","title":"Scope"},"description":"Set to `org` to change or delete a qualification group shared by every list (the ICP and Persona qualification groups). Admin keys only. Without it such a call answers 409 with code `shared_qualification_group`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"enrichment:delete","x-graph8-lifecycle":"active"},"get":{"tags":["Enrichment"],"summary":"Get Ai Configuration","description":"Read one AI group: prompt, model, inputs and output columns. Free.","operationId":"get_ai_configuration_enrichment_ai_configs__group_id__get","parameters":[{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"The AI group id.","title":"Group Id"},"description":"The AI group id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"},"put":{"tags":["Enrichment"],"summary":"Update Ai Configuration","description":"Edit an AI group in place. Free: editing runs nothing.\n\nOutput columns that already exist keep their data; the run condition is\nvalidated before anything is saved. A qualification group shared by every\nlist answers 409 unless `scope=org` (admin keys only).","operationId":"update_ai_configuration_enrichment_ai_configs__group_id__put","parameters":[{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"The AI group id.","title":"Group Id"},"description":"The AI group id."},{"name":"scope","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^org$"},{"type":"null"}],"description":"Set to `org` to change or delete a qualification group shared by every list (the ICP and Persona qualification groups). Admin keys only. Without it such a call answers 409 with code `shared_qualification_group`.","title":"Scope"},"description":"Set to `org` to change or delete a qualification group shared by every list (the ICP and Persona qualification groups). Admin keys only. Without it such a call answers 409 with code `shared_qualification_group`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateAIConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/enrichment/ai/configs/{group_id}/columns/{column_id}":{"delete":{"tags":["Enrichment"],"summary":"Delete Ai Config By Column","description":"Drop ONE column from an AI group. The group and its other columns stay.\n\nFree. `columns` is plural here where the app writes `column`, so the path\nreads the same way as every other collection in this contract. A column of\na qualification group shared by every list answers 409 unless `scope=org`\n(admin keys only).","operationId":"delete_ai_config_by_column_enrichment_ai_configs__group_id__columns__column_id__delete","parameters":[{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"AI group id.","title":"Group Id"},"description":"AI group id."},{"name":"column_id","in":"path","required":true,"schema":{"type":"string","description":"The single column to drop.","title":"Column Id"},"description":"The single column to drop."},{"name":"hard_delete","in":"query","required":false,"schema":{"type":"boolean","description":"Remove the configuration permanently instead of deactivating it. The values it already wrote are kept either way.","default":false,"title":"Hard Delete"},"description":"Remove the configuration permanently instead of deactivating it. The values it already wrote are kept either way."},{"name":"scope","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^org$"},{"type":"null"}],"description":"Set to `org` to change or delete a qualification group shared by every list (the ICP and Persona qualification groups). Admin keys only. Without it such a call answers 409 with code `shared_qualification_group`.","title":"Scope"},"description":"Set to `org` to change or delete a qualification group shared by every list (the ICP and Persona qualification groups). Admin keys only. Without it such a call answers 409 with code `shared_qualification_group`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"enrichment:delete","x-graph8-lifecycle":"active"}},"/enrichment/configs/{config_id}":{"put":{"tags":["Enrichment"],"summary":"Update Enrichment Config","description":"Change fields on an enrichment configuration. Free.\n\nWhatever keys are sent are written - the app takes a free-form body here\nand this forwards it unchanged rather than narrowing what the browser can\nalready do. `updated_by` is stamped from the calling key and cannot be\nsupplied. A qualification configuration shared by every list answers 409\nunless `scope=org` (admin keys only).","operationId":"update_enrichment_config_enrichment_configs__config_id__put","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"string","description":"Enrichment configuration id (UUID).","title":"Config Id"},"description":"Enrichment configuration id (UUID)."},{"name":"scope","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^org$"},{"type":"null"}],"description":"Set to `org` to change or delete a qualification group shared by every list (the ICP and Persona qualification groups). Admin keys only. Without it such a call answers 409 with code `shared_qualification_group`.","title":"Scope"},"description":"Set to `org` to change or delete a qualification group shared by every list (the ICP and Persona qualification groups). Admin keys only. Without it such a call answers 409 with code `shared_qualification_group`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EnrichmentConfigUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Enrichment"],"summary":"Delete Enrichment Config","description":"Remove an enrichment configuration. Free.\n\nA qualification configuration shared by every list answers 409 unless\n`scope=org` (admin keys only).","operationId":"delete_enrichment_config_enrichment_configs__config_id__delete","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"string","description":"Enrichment configuration id (UUID).","title":"Config Id"},"description":"Enrichment configuration id (UUID)."},{"name":"hard_delete","in":"query","required":false,"schema":{"type":"boolean","description":"Remove the configuration permanently instead of deactivating it. The values it already wrote are kept either way.","default":false,"title":"Hard Delete"},"description":"Remove the configuration permanently instead of deactivating it. The values it already wrote are kept either way."},{"name":"scope","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^org$"},{"type":"null"}],"description":"Set to `org` to change or delete a qualification group shared by every list (the ICP and Persona qualification groups). Admin keys only. Without it such a call answers 409 with code `shared_qualification_group`.","title":"Scope"},"description":"Set to `org` to change or delete a qualification group shared by every list (the ICP and Persona qualification groups). Admin keys only. Without it such a call answers 409 with code `shared_qualification_group`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"enrichment:delete","x-graph8-lifecycle":"active"},"get":{"tags":["Enrichment"],"summary":"Get Enrichment Configuration","description":"Read one configuration, including its full `config` body. Free.","operationId":"get_enrichment_configuration_enrichment_configs__config_id__get","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"string","description":"Configuration id (UUID).","title":"Config Id"},"description":"Configuration id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/waterfall/configs/{column_id}":{"delete":{"tags":["Enrichment"],"summary":"Delete Waterfall Config","description":"Remove a waterfall configuration. Free.\n\nPLURAL, beside the `GET`/`POST /enrichment/waterfall/configs` that already\nship. The app spells this one singular; two paths one letter apart do not\nbelong in a public contract.","operationId":"delete_waterfall_config_enrichment_waterfall_configs__column_id__delete","parameters":[{"name":"column_id","in":"path","required":true,"schema":{"type":"string","description":"Waterfall column id.","title":"Column Id"},"description":"Waterfall column id."},{"name":"hard_delete","in":"query","required":false,"schema":{"type":"boolean","description":"Remove the configuration permanently instead of deactivating it. The values it already wrote are kept either way.","default":false,"title":"Hard Delete"},"description":"Remove the configuration permanently instead of deactivating it. The values it already wrote are kept either way."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"enrichment:delete","x-graph8-lifecycle":"active"},"get":{"tags":["Enrichment"],"summary":"Get Waterfall Configuration","description":"Read one waterfall: its provider steps, in order, and its settings. Free.","operationId":"get_waterfall_configuration_enrichment_waterfall_configs__column_id__get","parameters":[{"name":"column_id","in":"path","required":true,"schema":{"type":"string","description":"The enrichment column id.","title":"Column Id"},"description":"The enrichment column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"},"put":{"tags":["Enrichment"],"summary":"Update Waterfall Configuration","description":"Replace a waterfall's steps and settings. DEFINES SPEND.\n\nGraded like its create sibling `POST /enrichment/waterfall/configs`: the\ndefinition picks which PAID providers run, `is_system_provider` charges\ngraph8 credits per call, `email_verification` adds a paid verification per\naddress, and `auto_update` keeps the column refreshing on its own.\n`config.org_id` is ignored; the key's organisation is used.","operationId":"update_waterfall_configuration_enrichment_waterfall_configs__column_id__put","parameters":[{"name":"column_id","in":"path","required":true,"schema":{"type":"string","description":"The enrichment column id.","title":"Column Id"},"description":"The enrichment column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateWaterfallConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/formula/configs/{column_id}":{"post":{"tags":["Enrichment"],"summary":"Create Formula Config","description":"Attach a formula to a column. FREE.\n\nA formula is evaluated locally from data already on the record, so neither\nsaving nor running one calls a provider or spends a credit. It is the\ncheapest way to derive a column.","operationId":"create_formula_config_enrichment_formula_configs__column_id__post","parameters":[{"name":"column_id","in":"path","required":true,"schema":{"type":"string","description":"Column the formula fills.","title":"Column Id"},"description":"Column the formula fills."},{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Scope the formula to one list. Omit for a global one.","title":"List Id"},"description":"Scope the formula to one list. Omit for a global one."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateFormulaConfigRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Enrichment"],"summary":"Delete Formula Config","description":"Remove a formula configuration. Free. Values already computed stay.","operationId":"delete_formula_config_enrichment_formula_configs__column_id__delete","parameters":[{"name":"column_id","in":"path","required":true,"schema":{"type":"string","description":"Column the formula fills.","title":"Column Id"},"description":"Column the formula fills."},{"name":"hard_delete","in":"query","required":false,"schema":{"type":"boolean","description":"Remove the configuration permanently instead of deactivating it. The values it already wrote are kept either way.","default":false,"title":"Hard Delete"},"description":"Remove the configuration permanently instead of deactivating it. The values it already wrote are kept either way."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"enrichment:delete","x-graph8-lifecycle":"active"},"get":{"tags":["Enrichment"],"summary":"Get Formula Configuration","description":"Read one formula column's definition. Free.","operationId":"get_formula_configuration_enrichment_formula_configs__column_id__get","parameters":[{"name":"column_id","in":"path","required":true,"schema":{"type":"string","description":"The enrichment column id.","title":"Column Id"},"description":"The enrichment column id."},{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Scope to a list's configuration.","title":"List Id"},"description":"Scope to a list's configuration."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"},"put":{"tags":["Enrichment"],"summary":"Update Formula Configuration","description":"Edit a formula column. Free. The new formula is validated before saving.","operationId":"update_formula_configuration_enrichment_formula_configs__column_id__put","parameters":[{"name":"column_id","in":"path","required":true,"schema":{"type":"string","description":"The enrichment column id.","title":"Column Id"},"description":"The enrichment column id."},{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Scope to a list's configuration.","title":"List Id"},"description":"Scope to a list's configuration."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateFormulaConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/enrichment/formula-templates":{"get":{"tags":["Enrichment"],"summary":"List Formula Templates","description":"Formula templates usable on a list. FREE.","operationId":"list_formula_templates_enrichment_formula_templates_get","parameters":[{"name":"list_id","in":"query","required":true,"schema":{"type":"integer","description":"Templates applicable to this list.","title":"List Id"},"description":"Templates applicable to this list."},{"name":"category","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to one category.","title":"Category"},"description":"Narrow to one category."},{"name":"include_system_templates","in":"query","required":false,"schema":{"type":"boolean","description":"Include graph8's built-in templates as well as the org's own.","default":true,"title":"Include System Templates"},"description":"Include graph8's built-in templates as well as the org's own."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"},"post":{"tags":["Enrichment"],"summary":"Create Formula Template","description":"Save a reusable formula-authoring template. FREE.\n\nA template is a stored prompt plus the fields it depends on; creating one\ncalls no model. It costs when someone later authors a formula from it.","operationId":"create_formula_template_enrichment_formula_templates_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateFormulaTemplateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/enrichment/ai-templates":{"get":{"tags":["Enrichment"],"summary":"List Ai Templates","description":"AI enrichment templates usable on a list. FREE.","operationId":"list_ai_templates_enrichment_ai_templates_get","parameters":[{"name":"list_id","in":"query","required":true,"schema":{"type":"integer","description":"Templates applicable to this list.","title":"List Id"},"description":"Templates applicable to this list."},{"name":"category","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to one category.","title":"Category"},"description":"Narrow to one category."},{"name":"include_system_templates","in":"query","required":false,"schema":{"type":"boolean","description":"Include graph8's built-in templates as well as the org's own.","default":true,"title":"Include System Templates"},"description":"Include graph8's built-in templates as well as the org's own."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/columns":{"post":{"tags":["Enrichment"],"summary":"Create Dynamic Column","description":"Add a custom column. FREE.\n\nOMITTING `list_id` CREATES A GLOBAL COLUMN, on every list in the\norganisation. That is the app's own default and it is the wider of the two\noutcomes, so pass a `list_id` unless you mean it.","operationId":"create_dynamic_column_enrichment_columns_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateDynamicColumnRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/enrichment/records/{record_id}/fields/{column_id}":{"patch":{"tags":["Enrichment"],"summary":"Update Enrichment Field","description":"Hand-edit one enriched cell. FREE.\n\nA manual correction: no provider is called and nothing is charged. A null\n`value` clears the cell rather than leaving it alone.\n\n`record_type` is closed to `contact` / `company` because it selects which\ntable the write lands in - a wrong value here would write to the wrong\nentity, which is worse than being refused.","operationId":"update_enrichment_field_enrichment_records__record_id__fields__column_id__patch","parameters":[{"name":"record_id","in":"path","required":true,"schema":{"type":"integer","description":"Record id.","title":"Record Id"},"description":"Record id."},{"name":"column_id","in":"path","required":true,"schema":{"type":"string","description":"Enrichment column id.","title":"Column Id"},"description":"Enrichment column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateEnrichmentFieldRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/enrichment/records/progress":{"post":{"tags":["Enrichment"],"summary":"Get Enrichment Records Progress","description":"Per-record progress for enrichments in flight. FREE - a read.\n\nPOST only because the record list is a structured body. It reports which\nprovider and step each record is on right now, which is what lets a client\nresume a view mid-run instead of showing a blank cell.\n\nThe app takes at most 500 ids and ignores the rest, so page through them\nrather than sending a whole list.","operationId":"get_enrichment_records_progress_enrichment_records_progress_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RecordProgressRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/analytics/field-distribution":{"get":{"tags":["Enrichment"],"summary":"Get Enrichment Field Distribution","description":"How completely each field is filled across the org. FREE.\n\nThe coverage view: which fields enrichment is actually improving, and which\nare being paid for and left empty.\n\nThe app handler takes `org_id` from a dependency rather than a user object.\nIt is supplied here from the VALIDATED KEY's own principal, never from the\nrequest - there is no body or query parameter that can change it.","operationId":"get_enrichment_field_distribution_enrichment_analytics_field_distribution_get","parameters":[{"name":"period","in":"query","required":false,"schema":{"type":"string","description":"Reporting window.","default":"last_7_days","title":"Period"},"description":"Reporting window."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/analytics/daily-activity":{"get":{"tags":["Enrichment"],"summary":"Get Enrichment Daily Activity","description":"Enrichment volume per day. FREE.\n\nRead beside `field-distribution`: this says how much ran, that one says\nwhether it landed anywhere useful.","operationId":"get_enrichment_daily_activity_enrichment_analytics_daily_activity_get","parameters":[{"name":"period","in":"query","required":false,"schema":{"type":"string","description":"Reporting window.","default":"last_7_days","title":"Period"},"description":"Reporting window."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/ai-formula/functions":{"get":{"tags":["Enrichment"],"summary":"List Formula Functions","description":"The functions a formula can call, with signature, description and an example each. Free and static.","operationId":"list_formula_functions_enrichment_ai_formula_functions_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormulaFunctionsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/fill-column/preview":{"post":{"tags":["Enrichment"],"summary":"Preview Fill Column","description":"What moving an enrichment column's values into a destination column would change. WRITES NOTHING.\n\n`target_records` is how many list records have a value to move; `non_empty_values` how many of them already hold a\ndestination value (\"overwrite\" replaces those, \"fill only empty rows\" keeps them). Standard `CONTACT_*` and\n`COMPANY_*` destinations are the shared CRM record, so a real fill shows on every list and syncs to the CRM.\nNeeds write access to the list.","operationId":"preview_fill_column_enrichment_fill_column_preview_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FillColumnPreviewBody"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FillColumnPreviewPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/find-people/configure":{"post":{"tags":["Enrichment"],"summary":"Configure Find People","description":"Find contacts at every company on a list. SPENDS CREDITS.\n\nThis reads as configuration and is not one. The search runs against the\nlicensed people corpus, and `auto_import` true imports the results with no\nreview step - so a single call can move thousands of contacts into a list.\n\n`max_total_people` is the ceiling that matters: it caps the whole run, not\neach company. `max_people_per_company` only shapes the distribution.\n\nFound contacts land with their details MASKED. Revealing them costs a\nfurther credit per contact.","operationId":"configure_find_people_enrichment_find_people_configure_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ConfigureFindPeopleRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/find-people/search-import":{"post":{"tags":["Enrichment"],"summary":"Search Import Find People","description":"Import people straight into a list. SPENDS CREDITS.\n\nTwo modes, and they differ enormously in blast radius:\n\n  * `contacts` - import exactly the records you pass. Bounded by your body.\n  * `icp_filters` - import EVERYTHING the filters match, up to\n    `max_result`. Unbounded unless you set that ceiling.\n\nUse `icp_filters` with `max_result` set, always. Without it the run is\nlimited only by how many people match, which is not a number you know\nbefore you pay for it.","operationId":"search_import_find_people_enrichment_find_people_search_import_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SearchImportRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/find-people/{config_id}":{"get":{"tags":["Enrichment"],"summary":"Get Find People Config","description":"Read a people-search configuration. FREE.","operationId":"get_find_people_config_enrichment_find_people__config_id__get","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"string","description":"Configuration id (UUID).","title":"Config Id"},"description":"Configuration id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"},"put":{"tags":["Enrichment"],"summary":"Update Find People Config","description":"Edit a people-search configuration. Free in itself.\n\nOmitted fields are left alone. Setting `auto_import` true here has the same\nconsequence it has at creation: results stop waiting for a human.","operationId":"update_find_people_config_enrichment_find_people__config_id__put","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"string","description":"Configuration id (UUID).","title":"Config Id"},"description":"Configuration id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateFindPeopleConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Enrichment"],"summary":"Delete Find People Config","description":"Remove a people-search configuration. Free.\n\n`hard_delete` DEFAULTS TO TRUE here, unlike every other delete on this\nsurface, which defaults to false. That asymmetry is the app's and is\ndocumented rather than quietly normalised - changing it would make this\nendpoint behave differently through the API than through the browser.","operationId":"delete_find_people_config_enrichment_find_people__config_id__delete","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"string","description":"Configuration id (UUID).","title":"Config Id"},"description":"Configuration id (UUID)."},{"name":"hard_delete","in":"query","required":false,"schema":{"type":"boolean","description":"TRUE BY DEFAULT, matching the app: the configuration is removed permanently rather than deactivated. Pass false to keep it. Contacts already imported are unaffected either way.","default":true,"title":"Hard Delete"},"description":"TRUE BY DEFAULT, matching the app: the configuration is removed permanently rather than deactivated. Pass false to keep it. Contacts already imported are unaffected either way."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"enrichment:delete","x-graph8-lifecycle":"active"}},"/enrichment/find-people/{config_id}/results/{company_id}":{"get":{"tags":["Enrichment"],"summary":"Get Find People Results","description":"What the search found for one company. FREE.\n\nReading results costs nothing - the search already paid for them. Contact\ndetails are masked until unlocked.","operationId":"get_find_people_results_enrichment_find_people__config_id__results__company_id__get","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"string","description":"Configuration id (UUID).","title":"Config Id"},"description":"Configuration id (UUID)."},{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","description":"Which company's results to read.","title":"Company Id"},"description":"Which company's results to read."},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to one result status.","title":"Status"},"description":"Narrow to one result status."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":25,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/find-people/{config_id}/import":{"post":{"tags":["Enrichment"],"summary":"Import Find People Results","description":"Move found contacts into the destination list. SPENDS CREDITS.\n\nOMITTING BOTH `company_ids` AND `result_ids` IMPORTS EVERYTHING PENDING,\nand the body is optional - so a bare POST imports the lot.\n\n`result_ids` overrides `company_ids` when both are given; it does not\nintersect them.","operationId":"import_find_people_results_enrichment_find_people__config_id__import_post","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"string","description":"Configuration id (UUID).","title":"Config Id"},"description":"Configuration id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ImportFindPeopleRequest","default":{}}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/list-routing/rules":{"post":{"tags":["Enrichment"],"summary":"Create Routing Rule","description":"Move records from one list to another when they match. FREE to create.\n\n`schedule_type` decides how long this lives: `one_time` runs when asked,\n`continuous` keeps matching NEW records for as long as the rule exists. A\ncontinuous rule combined with an auto-enriching destination is a standing\nspend, so read the two together.\n\n`column_config.mode` `all` copies every enrichment column with the record -\ndata you have already paid for travels with it rather than being re-bought.","operationId":"create_routing_rule_enrichment_list_routing_rules_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateRoutingRuleRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"},"get":{"tags":["Enrichment"],"summary":"List Routing Rules","description":"Every routing rule in the organisation. FREE.\n\nThe inventory of what moves records around without anyone asking.","operationId":"list_routing_rules_enrichment_list_routing_rules_get","parameters":[{"name":"source_list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Only rules reading this list.","title":"Source List Id"},"description":"Only rules reading this list."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/list-routing/rules/{rule_id}":{"get":{"tags":["Enrichment"],"summary":"Get Routing Rule","description":"Read one routing rule. FREE.","operationId":"get_routing_rule_enrichment_list_routing_rules__rule_id__get","parameters":[{"name":"rule_id","in":"path","required":true,"schema":{"type":"string","description":"Routing rule id (UUID).","title":"Rule Id"},"description":"Routing rule id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Enrichment"],"summary":"Delete Routing Rule","description":"Remove a routing rule. Free. Records it already moved stay where they are.","operationId":"delete_routing_rule_enrichment_list_routing_rules__rule_id__delete","parameters":[{"name":"rule_id","in":"path","required":true,"schema":{"type":"string","description":"Routing rule id (UUID).","title":"Rule Id"},"description":"Routing rule id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"enrichment:delete","x-graph8-lifecycle":"active"}},"/enrichment/list-routing/generate-filter":{"post":{"tags":["Enrichment"],"summary":"Generate Routing Filter","description":"Turn a sentence into routing conditions. COSTS AN AI CALL.\n\nAdvisory: it returns conditions to review, and creates no rule. Nothing\nmoves until you post them to `/enrichment/list-routing/rules`.","operationId":"generate_routing_filter_enrichment_list_routing_generate_filter_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/GenerateFilterRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/lists/pipeline-templates":{"get":{"tags":["Enrichment"],"summary":"List Pipeline Templates","description":"Ready-made enrichment pipelines. FREE.","operationId":"list_pipeline_templates_enrichment_lists_pipeline_templates_get","parameters":[{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Templates applicable to this list.","title":"List Id"},"description":"Templates applicable to this list."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/lists/pipeline-runs/{run_id}":{"get":{"tags":["Enrichment"],"summary":"Get Pipeline Run","description":"How a pipeline run is going. FREE - polling costs nothing.","operationId":"get_pipeline_run_enrichment_lists_pipeline_runs__run_id__get","parameters":[{"name":"run_id","in":"path","required":true,"schema":{"type":"string","description":"Pipeline run id.","title":"Run Id"},"description":"Pipeline run id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/lists/{list_id}/pipeline-step-options":{"get":{"tags":["Enrichment"],"summary":"List Pipeline Step Options","description":"Configs that can be used as pipeline steps on this list. FREE.\n\nThe menu a pipeline is assembled from - AI groups and waterfall columns\nalready configured, with the columns each writes.","operationId":"list_pipeline_step_options_enrichment_lists__list_id__pipeline_step_options_get","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","title":"List Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/lists/{list_id}/pipelines/ai-draft":{"post":{"tags":["Enrichment"],"summary":"Draft Pipeline With Ai","description":"Draft a pipeline from a stated goal. COSTS AN AI CALL.\n\nReturns a draft and nothing else: no pipeline is created, saved or run, so\nthe only cost is the model call that writes it. `prioritize_cost` true asks\nthe drafter to prefer cheaper steps, which is worth leaving on.","operationId":"draft_pipeline_with_ai_enrichment_lists__list_id__pipelines_ai_draft_post","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","title":"List Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AIPipelineDraftRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/lists/{list_id}/pipelines/{pipeline_id}/enabled":{"post":{"tags":["Enrichment"],"summary":"Set Pipeline Enabled","description":"Turn a pipeline on or off. TURNING IT ON STARTS SPENDING.\n\nA pipeline is a chain of enrichment steps over a whole list. Enabling it\nruns them, and every step that calls a provider or a model costs - so this\none boolean is the most consequential field on this route.\n\nExplicit rather than a toggle, so a retried request cannot restart a\npipeline somebody just stopped.","operationId":"set_pipeline_enabled_enrichment_lists__list_id__pipelines__pipeline_id__enabled_post","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","title":"List Id"}},{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","description":"Pipeline id (UUID).","title":"Pipeline Id"},"description":"Pipeline id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetPipelineEnabledRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/ai/qualification/templates/{template_id}":{"put":{"tags":["Enrichment"],"summary":"Update Qualification Template","description":"Edit a qualification template. Free to edit.\n\nADMIN ONLY, matching the app - a template decides how every record in the\norganisation is scored, so it is not ordinary list configuration.\n\nThe prompt has a 100-character MINIMUM. That is the app's, and it is a\nquality floor rather than an accident: a two-word qualification prompt\nscores everything the same way and bills for it.","operationId":"update_qualification_template_enrichment_ai_qualification_templates__template_id__put","parameters":[{"name":"template_id","in":"path","required":true,"schema":{"type":"string","description":"Qualification template id (UUID).","title":"Template Id"},"description":"Qualification template id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateQualificationTemplateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/enrichment/ai/qualification/generate-templates":{"post":{"tags":["Enrichment"],"summary":"Generate Qualification Templates","description":"Build qualification templates from the org's ICPs and personas. COSTS AI CALLS.\n\nADMIN ONLY. Mirrors every active ICP into a company template and every\npersona into a contact template.\n\nPARTIAL COVERAGE IS A SUCCESS, not an error: read `source_counts` and\n`skipped_entities` in the response rather than the status code, or you will\nthink it worked when half the org has no template.","operationId":"generate_qualification_templates_enrichment_ai_qualification_generate_templates_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/ai/qualification/estimate-all":{"post":{"tags":["Enrichment"],"summary":"Estimate All Qualification Templates","description":"Price EVERY template against one list, side by side. CHARGES NOTHING.\n\n\"Which ICP is worth qualifying this list against?\" answered without\nspending a credit. It creates no config, no column and no assignment -\ncancelling leaves zero footprint.\n\nTemplates that cannot run on the list come back with a per-item error\nrather than failing the comparison, so read the items, not the status.\n\nRequires WRITE access to the list even though it only reads, matching the\napp: pricing a run the caller could never start is a review screen that\nlies.","operationId":"estimate_all_qualification_templates_enrichment_ai_qualification_estimate_all_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EstimateAllRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/ai/qualification/fit-landscape":{"get":{"tags":["Enrichment"],"summary":"Get Qualification Fit Landscape","description":"How much of the org fits each ICP and persona. FREE.\n\nCumulative: fits accumulate across runs and are never automatically\nremoved, so these counts describe everything ever qualified rather than a\ncurrent snapshot. Read `last_written` before treating them as fresh.","operationId":"get_qualification_fit_landscape_enrichment_ai_qualification_fit_landscape_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/configs/{config_id}/assignments":{"get":{"tags":["Enrichment"],"summary":"List Config Assignments","description":"Which lists an enrichment column is visible on. FREE.\n\nA column's DATA is entity-keyed, so a record that moves lists keeps its\nvalues; assignments control visibility, not storage. `org_wide` true means\nthe config applies everywhere and has no per-list assignments at all.","operationId":"list_config_assignments_enrichment_configs__config_id__assignments_get","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Config Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"},"post":{"tags":["Enrichment"],"summary":"Assign Enrichment Configuration","description":"Make a configuration available on more lists. Free.\n\nIdempotent: a list that already has it, or is its home list, is skipped.\nNeeds write access to the configuration's home list AND to every target.","operationId":"assign_enrichment_configuration_enrichment_configs__config_id__assignments_post","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Config Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssignListsRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/enrichment/configs/{config_id}/assignments/{list_id}":{"delete":{"tags":["Enrichment"],"summary":"Unassign Config From List","description":"Stop showing a column on one list. Free.\n\nThe values stay in the database - this hides the column, it does not delete\nenrichment you paid for. Re-assigning brings them back.\n\nBOTH gates are declared: the config's home list and the list being\ndetached. They are different lists and a caller can easily have access to\none and not the other.","operationId":"unassign_config_from_list_enrichment_configs__config_id__assignments__list_id__delete","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Config Id"}},{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","title":"List Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"enrichment:delete","x-graph8-lifecycle":"active"}},"/enrichment/auto-enrichment/configs/{config_id}":{"patch":{"tags":["Enrichment"],"summary":"Update Auto Enrichment Config","description":"Edit an auto-enrichment configuration. CAN ARM ONGOING SPEND.\n\n`trigger_on_insert` true means every record inserted from now on is\nenriched automatically, with no further call. The PATCH is free; what it\nswitches on is not.","operationId":"update_auto_enrichment_config_enrichment_auto_enrichment_configs__config_id__patch","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"string","description":"Configuration id (UUID).","title":"Config Id"},"description":"Configuration id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateAutoEnrichmentConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Enrichment"],"summary":"Delete Auto Enrichment Config","description":"Remove an auto-enrichment configuration. Free, and it stops the spend.","operationId":"delete_auto_enrichment_config_enrichment_auto_enrichment_configs__config_id__delete","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"string","description":"Configuration id (UUID).","title":"Config Id"},"description":"Configuration id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"enrichment:delete","x-graph8-lifecycle":"active"},"get":{"tags":["Enrichment"],"summary":"Get Auto Enrichment Config","description":"Read one auto-enrichment config. Free.","operationId":"get_auto_enrichment_config_enrichment_auto_enrichment_configs__config_id__get","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"string","description":"Auto-enrichment config id (UUID).","title":"Config Id"},"description":"Auto-enrichment config id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/record-sync/{entity_type}/policy":{"put":{"tags":["Enrichment"],"summary":"Update Record Sync Policy","description":"Decide how enriched data is written back onto records. ARMS ONGOING SPEND.\n\n`policy.enabled` true starts recurring reconciliation on\n`policy.schedule`: enrichment runs against the records in\n`policy.audience_ids` and writes results onto them, repeatedly, with nobody\nin the loop. That is a standing credit cost, which is why this is graded as\na spend rather than a setting.\n\n`policy.default_field.mode` decides what happens to data the customer\nalready has. `replace` OVERWRITES their values with the source's.\n`preserve` never does. `fill_missing` - the default - only fills blanks.\nGetting this wrong is not a billing problem, it is a data-loss one.\n\n`expected_version` is the version you READ. A stale value is rejected, so\ntwo editors cannot silently overwrite each other's policy.","operationId":"update_record_sync_policy_enrichment_record_sync__entity_type__policy_put","parameters":[{"name":"entity_type","in":"path","required":true,"schema":{"enum":["contact","company"],"type":"string","description":"Which record kind this policy governs.","title":"Entity Type"},"description":"Which record kind this policy governs."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateMashupSyncPolicyRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/record-sync/{entity_type}/review":{"post":{"tags":["Enrichment"],"summary":"Review Record Sync Change","description":"Resolve one flagged record-sync change. Free.\n\n`retry` re-applies the change the policy wanted to make; `preserve` keeps\nthe record as it is and stops asking.\n\n`expected_version` guards against resolving a conflict against a policy\nthat has since moved.\n\nA LIMITATION WORTH KNOWING: `local_id` and `event_id` identify a conflict\nthat this contract does not yet publish a way to LIST. The app has sibling\nreads for that (`/status`, `/history`, `/preview`) and none of them are\npublished today - through this API those ids have to come from elsewhere.\nSee the PR description; it is a gap, not a design.","operationId":"review_record_sync_change_enrichment_record_sync__entity_type__review_post","parameters":[{"name":"entity_type","in":"path","required":true,"schema":{"enum":["contact","company"],"type":"string","description":"Which record kind.","title":"Entity Type"},"description":"Which record kind."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ReviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/enrichment/companies/gtm-profile":{"get":{"tags":["Enrichment"],"summary":"Get Company Gtm Profile","description":"What a company sells, who it serves, and its buyer titles. FREE.\n\nRead from a pre-computed corpus rather than researched on demand, so\ndespite being a company lookup it spends no credit.\n\nABSENCE IS A 200, NEVER A 404. Only about a third of domains have a\nprofile, so `found: false` with a null profile is the ordinary answer, not\nan error - and it is deliberately indistinguishable from the corpus being\nunavailable. Never present absence to a user or a model as a fact about the\ncompany.\n\nREADING HYDRATES: a miss that the corpus can satisfy is written back into\nthe organisation's own table as a side effect. That is the app's design -\nsomebody asking about a domain is the signal that the domain matters - and\nit means this read is not perfectly side-effect-free.","operationId":"get_company_gtm_profile_enrichment_companies_gtm_profile_get","parameters":[{"name":"domain","in":"query","required":true,"schema":{"type":"string","description":"Company domain to look up.","title":"Domain"},"description":"Company domain to look up."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/waterfall/jobs/{job_id}/progress":{"get":{"tags":["Enrichment"],"summary":"Get Waterfall Job Progress","description":"How a waterfall enrichment job is going. FREE - polling costs nothing.\n\nPer-provider progress for a job already running. `GET /enrichment/jobs/\n{job_id}` is the general job read; this one breaks the waterfall down by\nthe provider each record is currently on.","operationId":"get_waterfall_job_progress_enrichment_waterfall_jobs__job_id__progress_get","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","description":"Waterfall job id.","title":"Job Id"},"description":"Waterfall job id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/configs":{"get":{"tags":["Enrichment"],"summary":"List Enrichment Configurations","description":"List every enrichment configuration in the organisation. Free.","operationId":"list_enrichment_configurations_enrichment_configs_get","parameters":[{"name":"config_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":50},{"type":"null"}],"description":"Filter by type, e.g. `ai`, `waterfall`.","title":"Config Type"},"description":"Filter by type, e.g. `ai`, `waterfall`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"},"post":{"tags":["Enrichment"],"summary":"Create Enrichment Configuration","description":"Create an AI or waterfall configuration. Free: saving runs nothing.\n\nThe organisation and author always come from the API key; the app handler\nsets both itself and takes neither from the body.","operationId":"create_enrichment_configuration_enrichment_configs_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateEnrichmentConfigRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/enrichment/waterfall/templates":{"get":{"tags":["Enrichment"],"summary":"List Waterfall Templates","description":"Pre-built waterfalls for standard fields, with recommended providers. Free.","operationId":"list_waterfall_templates_enrichment_waterfall_templates_get","parameters":[{"name":"field","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":120},{"type":"null"}],"description":"One field, e.g. `CONTACT_WORK_EMAIL`.","title":"Field"},"description":"One field, e.g. `CONTACT_WORK_EMAIL`."},{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Only templates for this list's record type.","title":"List Id"},"description":"Only templates for this list's record type."},{"name":"include_optional_steps","in":"query","required":false,"schema":{"type":"boolean","description":"Include `config.optional_steps`: further providers that can fill the field. They run only when you pass them in `providers`, never in the default order. `supported_providers` lists default plus optional.","default":true,"title":"Include Optional Steps"},"description":"Include `config.optional_steps`: further providers that can fill the field. They run only when you pass them in `providers`, never in the default order. `supported_providers` lists default plus optional."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/formula/configs/{column_id}/run":{"post":{"tags":["Enrichment"],"summary":"Run Formula Column","description":"Compute a formula column for records. Free: formulas run locally.\n\nWRITES to every record in scope. With no ids and no `mode` that is the\nlist's records up to `max_records`; `dry_run` validates without writing.","operationId":"run_formula_column_enrichment_formula_configs__column_id__run_post","parameters":[{"name":"column_id","in":"path","required":true,"schema":{"type":"string","description":"The enrichment column id.","title":"Column Id"},"description":"The enrichment column id."},{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Scope to a list's configuration.","title":"List Id"},"description":"Scope to a list's configuration."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/RunFormulaRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/enrichment/ai-formula/generate":{"post":{"tags":["Enrichment"],"summary":"Generate Formula With Ai","description":"Write a formula from a plain-language description. CHARGES: one model call.\n\nRefused with 402 before the model runs when the organisation has no credit.\nThe fields the formula may use are read from your data, not from `fields`.","operationId":"generate_formula_with_ai_enrichment_ai_formula_generate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AIFormulaGenerateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/ai-formula/validate":{"post":{"tags":["Enrichment"],"summary":"Validate Formula","description":"Check a formula's syntax and the fields it references. Free, no model.","operationId":"validate_formula_enrichment_ai_formula_validate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AIFormulaValidateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/ai-formula/preview":{"post":{"tags":["Enrichment"],"summary":"Preview Formula","description":"Evaluate a formula over sample rows you supply. Free: local, no model, no writes.","operationId":"preview_formula_enrichment_ai_formula_preview_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AIFormulaPreviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/active-jobs":{"get":{"tags":["Enrichment"],"summary":"List Active Enrichment Jobs","description":"Enrichment jobs running, paused or pending in the last six hours, with\nlive progress. Free. Organisation-wide, at most twenty.","operationId":"list_active_enrichment_jobs_enrichment_active_jobs_get","parameters":[{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Only jobs on this list.","title":"List Id"},"description":"Only jobs on this list."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/jobs/{job_id}/pause":{"post":{"tags":["Enrichment"],"summary":"Pause Enrichment Job","description":"Pause a running job. Free, and it stops further charges until resumed.","operationId":"pause_enrichment_job_enrichment_jobs__job_id__pause_post","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","description":"Enrichment job id (UUID).","title":"Job Id"},"description":"Enrichment job id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/JobControlRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/enrichment/jobs/{job_id}/resume":{"post":{"tags":["Enrichment"],"summary":"Resume Enrichment Job","description":"Resume a paused job. CHARGES: the job carries on enriching, and billing,\nthe records it had not reached.","operationId":"resume_enrichment_job_enrichment_jobs__job_id__resume_post","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","description":"Enrichment job id (UUID).","title":"Job Id"},"description":"Enrichment job id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/jobs/{job_id}/cancel":{"post":{"tags":["Enrichment"],"summary":"Cancel Enrichment Job","description":"Cancel a running or paused job. Free, and it cannot be undone.\n\nRecords already enriched keep their data and their charge; nothing further\nis enriched.","operationId":"cancel_enrichment_job_enrichment_jobs__job_id__cancel_post","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","description":"Enrichment job id (UUID).","title":"Job Id"},"description":"Enrichment job id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/JobControlRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/enrichment/ai/batch/enrich":{"post":{"tags":["Enrichment"],"summary":"Start Ai Batch Enrichment","description":"Run a saved AI group over a list. CHARGES per record.\n\n`enrichment_mode: all` runs EVERY record in the list. Send `dry_run: true`\nfirst: it returns the record count and credits per record and starts\nnothing. Poll the returned job with `GET /enrichment/ai/batch/jobs/{job_id}/status`.","operationId":"start_ai_batch_enrichment_enrichment_ai_batch_enrich_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AIBatchEnrichmentRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/ai/batch/jobs/{job_id}/status":{"get":{"tags":["Enrichment"],"summary":"Get Ai Batch Job Status","description":"Progress and credits charged so far for an AI batch job. Free.","operationId":"get_ai_batch_job_status_enrichment_ai_batch_jobs__job_id__status_get","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","maxLength":64,"description":"The batch job id.","title":"Job Id"},"description":"The batch job id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/analytics/metrics":{"get":{"tags":["Enrichment"],"summary":"Get Enrichment Metrics","description":"Enrichment volume, success rate and cost for a period. Free.","operationId":"get_enrichment_metrics_enrichment_analytics_metrics_get","parameters":[{"name":"period","in":"query","required":false,"schema":{"enum":["last_7_days","last_30_days","last_90_days","current_month","last_month"],"type":"string","default":"last_7_days","title":"Period"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/analytics/trends":{"get":{"tags":["Enrichment"],"summary":"Get Enrichment Trends","description":"Enrichment counts over time, by day, week or month. Free.","operationId":"get_enrichment_trends_enrichment_analytics_trends_get","parameters":[{"name":"period","in":"query","required":false,"schema":{"enum":["last_7_days","last_30_days","last_90_days","current_month","last_month"],"type":"string","default":"last_7_days","title":"Period"}},{"name":"granularity","in":"query","required":false,"schema":{"enum":["day","week","month"],"type":"string","default":"day","title":"Granularity"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/lists/{list_id}/pipelines":{"get":{"tags":["Enrichment"],"summary":"List List Pipelines","description":"The list's pipelines, each with its most recent run. Free.","operationId":"list_list_pipelines_enrichment_lists__list_id__pipelines_get","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","title":"List Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"},"post":{"tags":["Enrichment"],"summary":"Create List Pipeline","description":"Create a pipeline of enrichment steps on a list. CAN ARM SPEND.\n\n`enabled` defaults to false. Set to true, the pipeline runs its steps over\nthe list, and each enrichment step charges per record. Price it first with\n`POST .../pipelines/{pipeline_id}/estimate`. An `inline_config` step creates\nthe AI or waterfall column it needs as part of the save.","operationId":"create_list_pipeline_enrichment_lists__list_id__pipelines_post","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","title":"List Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SaveListPipelineRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/lists/{list_id}/pipelines/from-template":{"post":{"tags":["Enrichment"],"summary":"Create List Pipeline From Template","description":"Build a pipeline from a pre-built recipe. Free: it is saved DISABLED.\n\nCreates any columns the recipe needs. Instantiating the same recipe again\nupdates the existing pipeline rather than adding a second one.","operationId":"create_list_pipeline_from_template_enrichment_lists__list_id__pipelines_from_template_post","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","title":"List Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/InstantiatePipelineTemplateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/enrichment/lists/{list_id}/pipelines/{pipeline_id}":{"put":{"tags":["Enrichment"],"summary":"Update List Pipeline","description":"Replace a pipeline's steps. CAN ARM SPEND when `enabled` is true.\n\n`enabled` omitted keeps the pipeline's current state.","operationId":"update_list_pipeline_enrichment_lists__list_id__pipelines__pipeline_id__put","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","title":"List Id"}},{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","description":"Pipeline id (UUID).","title":"Pipeline Id"},"description":"Pipeline id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateListPipelineRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Enrichment"],"summary":"Delete List Pipeline","description":"Delete a pipeline. Refused with 409 while it is running.","operationId":"delete_list_pipeline_enrichment_lists__list_id__pipelines__pipeline_id__delete","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","title":"List Id"}},{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","description":"Pipeline id (UUID).","title":"Pipeline Id"},"description":"Pipeline id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"enrichment:delete","x-graph8-lifecycle":"active"}},"/enrichment/lists/{list_id}/pipelines/{pipeline_id}/estimate":{"post":{"tags":["Enrichment"],"summary":"Estimate List Pipeline","description":"Price a pipeline run before starting it. FREE, and it starts nothing.\n\nAn upper bound: run conditions are ignored, so a pipeline that filters most\nrecords out of its expensive steps will cost less than this.","operationId":"estimate_list_pipeline_enrichment_lists__list_id__pipelines__pipeline_id__estimate_post","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","title":"List Id"}},{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","description":"Pipeline id (UUID).","title":"Pipeline Id"},"description":"Pipeline id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/lists/{list_id}/pipelines/{pipeline_id}/runs":{"post":{"tags":["Enrichment"],"summary":"Run List Pipeline","description":"Run a pipeline over its list now. CHARGES per record, per step.\n\nAlso ENABLES a disabled pipeline, as the app does: running it is the\nconsent. 409 if it is already running.","operationId":"run_list_pipeline_enrichment_lists__list_id__pipelines__pipeline_id__runs_post","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","title":"List Id"}},{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","description":"Pipeline id (UUID).","title":"Pipeline Id"},"description":"Pipeline id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"},"get":{"tags":["Enrichment"],"summary":"List List Pipeline Runs","description":"Finished runs of a pipeline, newest first, with per-step progress. Free.","operationId":"list_list_pipeline_runs_enrichment_lists__list_id__pipelines__pipeline_id__runs_get","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","title":"List Id"}},{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","description":"Pipeline id (UUID).","title":"Pipeline Id"},"description":"Pipeline id (UUID)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"default":10,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/lists/{list_id}/pipelines/{pipeline_id}/cancel":{"post":{"tags":["Enrichment"],"summary":"Cancel List Pipeline Run","description":"Stop the pipeline's active run. Free.\n\nThe step in flight finishes; no further step starts.","operationId":"cancel_list_pipeline_run_enrichment_lists__list_id__pipelines__pipeline_id__cancel_post","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","title":"List Id"}},{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","description":"Pipeline id (UUID).","title":"Pipeline Id"},"description":"Pipeline id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/enrichment/ai/qualification/templates":{"get":{"tags":["Enrichment"],"summary":"List Qualification Templates","description":"The organisation's qualification templates, and whether it has the\nsources to qualify contacts at all. Free.","operationId":"list_qualification_templates_enrichment_ai_qualification_templates_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/ai/qualification/run":{"post":{"tags":["Enrichment"],"summary":"Run Qualification","description":"Qualify every record on a list against a template. CHARGES per record.\n\nCreates the qualification column if the list does not have one yet. Price\nit first with `POST /enrichment/ai/qualification/estimate`. `requalify`\nre-runs, and re-charges, records that already have a verdict.","operationId":"run_qualification_enrichment_ai_qualification_run_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RunQualificationRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/ai/qualification/estimate":{"post":{"tags":["Enrichment"],"summary":"Estimate Qualification","description":"Price a qualification run. FREE: creates no column, no config, nothing.\n\nDeduplication-aware, so records sharing a company are priced once.","operationId":"estimate_qualification_enrichment_ai_qualification_estimate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RunQualificationRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/list-routing/rules/preview":{"post":{"tags":["Enrichment"],"summary":"Preview Routing Rule","description":"Count the contacts a set of routing conditions would match. Free, moves nothing.","operationId":"preview_routing_rule_enrichment_list_routing_rules_preview_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PreviewRoutingRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/list-routing/rules/{rule_id}/execute":{"post":{"tags":["Enrichment"],"summary":"Execute Routing Rule","description":"Run a routing rule now: matching contacts are moved to its destination\nlist. Free. Needs write access to both the source and destination lists.","operationId":"execute_routing_rule_enrichment_list_routing_rules__rule_id__execute_post","parameters":[{"name":"rule_id","in":"path","required":true,"schema":{"type":"string","description":"Routing rule id (UUID).","title":"Rule Id"},"description":"Routing rule id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/enrichment/find-people/{config_id}/run":{"post":{"tags":["Enrichment"],"summary":"Run Find People","description":"Find people at the list's companies. CHARGES per company searched.\n\n`all_rows` searches every company on the list; `first_10` is a cheap trial;\n`selected` searches only `record_ids`.","operationId":"run_find_people_enrichment_find_people__config_id__run_post","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"string","description":"Find-people configuration id (UUID).","title":"Config Id"},"description":"Find-people configuration id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RunFindPeopleRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/find-people/{config_id}/preview":{"post":{"tags":["Enrichment"],"summary":"Preview Find People","description":"Run a find-people configuration for ONE company and return who it finds,\nwithout saving. SEARCHES THE LICENSED PEOPLE CORPUS, so it is graded as a\nspend rather than a free preview.","operationId":"preview_find_people_enrichment_find_people__config_id__preview_post","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"string","description":"Find-people configuration id (UUID).","title":"Config Id"},"description":"Find-people configuration id (UUID)."},{"name":"company_id","in":"query","required":true,"schema":{"type":"integer","description":"The company to preview.","title":"Company Id"},"description":"The company to preview."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/auto-enrichment/configs":{"post":{"tags":["Enrichment"],"summary":"Create Auto Enrichment Config","description":"Enrich every record that lands on a list. ARMS ONGOING SPEND.\n\nFrom now on each record added to `audience_id` is enriched by the waterfall\nor AI group `column_id`, and charged, with no further call. Needs write\naccess to the list; the column must already be available on it. Turn it off\nwith `PATCH` or `DELETE /enrichment/auto-enrichment/configs/{config_id}`.","operationId":"create_auto_enrichment_config_enrichment_auto_enrichment_configs_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateAutoEnrichmentConfigRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"},"get":{"tags":["Enrichment"],"summary":"List Auto Enrichment Configs","description":"Every auto-enrichment config, or one list's. Free.\n\nWorth reading before an audit of where credit is going: these are spends\nnobody triggers by hand.","operationId":"list_auto_enrichment_configs_enrichment_auto_enrichment_configs_get","parameters":[{"name":"audience_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":1},{"type":"null"}],"description":"Only this list's configs.","title":"Audience Id"},"description":"Only this list's configs."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/auto-enrichment/settings":{"get":{"tags":["Enrichment"],"summary":"Get Auto Enrichment Settings","description":"Organisation-wide auto-enrichment settings for contacts and companies. Free.","operationId":"get_auto_enrichment_settings_enrichment_auto_enrichment_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/auto-enrichment/settings/{entity_type}":{"put":{"tags":["Enrichment"],"summary":"Update Auto Enrichment Settings","description":"Turn organisation-wide auto-enrichment on or off for a record kind.\nARMS ONGOING SPEND when `enabled` is true.\n\n`enabled` DEFAULTS TO TRUE, so a body that only sets `default_rule` also\nswitches auto-enrichment on. `default_rule` decides whether enriched data\nmay overwrite what is already on a record.","operationId":"update_auto_enrichment_settings_enrichment_auto_enrichment_settings__entity_type__put","parameters":[{"name":"entity_type","in":"path","required":true,"schema":{"enum":["contact","company"],"type":"string","description":"Which record kind.","title":"Entity Type"},"description":"Which record kind."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateAutoEnrichmentSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/record-sync/{entity_type}/fields":{"get":{"tags":["Enrichment"],"summary":"List Record Sync Fields","description":"The fields a record-sync policy can govern, for `fields` in the policy. Free.","operationId":"list_record_sync_fields_enrichment_record_sync__entity_type__fields_get","parameters":[{"name":"entity_type","in":"path","required":true,"schema":{"enum":["contact","company"],"type":"string","description":"Which record kind.","title":"Entity Type"},"description":"Which record kind."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/record-sync/{entity_type}/lists":{"get":{"tags":["Enrichment"],"summary":"List Record Sync Lists","description":"Lists a record-sync policy can target, for `audience_ids`. Free.","operationId":"list_record_sync_lists_enrichment_record_sync__entity_type__lists_get","parameters":[{"name":"entity_type","in":"path","required":true,"schema":{"enum":["contact","company"],"type":"string","description":"Which record kind.","title":"Entity Type"},"description":"Which record kind."},{"name":"search","in":"query","required":false,"schema":{"type":"string","maxLength":200,"default":"","title":"Search"}},{"name":"after","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Cursor: the last list id of the previous page.","default":0,"title":"After"},"description":"Cursor: the last list id of the previous page."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/record-sync/{entity_type}/status":{"get":{"tags":["Enrichment"],"summary":"Get Record Sync Status","description":"The saved policy, its `version`, and the state of the current run. Free.\n\nRead `version` here before writing the policy or requesting a run: both\nrefuse a stale `expected_version`.","operationId":"get_record_sync_status_enrichment_record_sync__entity_type__status_get","parameters":[{"name":"entity_type","in":"path","required":true,"schema":{"enum":["contact","company"],"type":"string","description":"Which record kind.","title":"Entity Type"},"description":"Which record kind."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/record-sync/{entity_type}/history":{"get":{"tags":["Enrichment"],"summary":"List Record Sync History","description":"Per-record sync deliveries, newest first. Free.\n\nEach carries the `local_id` and `event_id` that\n`POST /enrichment/record-sync/{entity_type}/review` and `.../preview` take.","operationId":"list_record_sync_history_enrichment_record_sync__entity_type__history_get","parameters":[{"name":"entity_type","in":"path","required":true,"schema":{"enum":["contact","company"],"type":"string","description":"Which record kind.","title":"Entity Type"},"description":"Which record kind."},{"name":"state","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":30},{"type":"null"}],"description":"Only deliveries in this state.","title":"State"},"description":"Only deliveries in this state."},{"name":"before","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"description":"Cursor: only deliveries created before this.","title":"Before"},"description":"Cursor: only deliveries created before this."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/enrichment/record-sync/{entity_type}/run":{"post":{"tags":["Enrichment"],"summary":"Run Record Sync","description":"Request a sync run now, under the saved policy. CAN SPEND.\n\nThe run applies the policy's enrichment to its records, up to\n`max_records_per_run`. Refused with 409 unless the policy is enabled and not\npaused, or when `expected_version` is stale. A run already in progress is\nreturned rather than a second one started.","operationId":"run_record_sync_enrichment_record_sync__entity_type__run_post","parameters":[{"name":"entity_type","in":"path","required":true,"schema":{"enum":["contact","company"],"type":"string","description":"Which record kind.","title":"Entity Type"},"description":"Which record kind."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RecordSyncRunRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/enrichment/record-sync/{entity_type}/preview":{"post":{"tags":["Enrichment"],"summary":"Preview Record Sync","description":"Show what syncing one record would change. Free, and changes nothing.\n\nPass `policy` to see the effect of a policy before saving it.","operationId":"preview_record_sync_enrichment_record_sync__entity_type__preview_post","parameters":[{"name":"entity_type","in":"path","required":true,"schema":{"enum":["contact","company"],"type":"string","description":"Which record kind.","title":"Entity Type"},"description":"Which record kind."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RecordSyncPreviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/workbench/target-fields":{"get":{"tags":["Workbench"],"summary":"List Workbench Target Fields","description":"The canonical fields a workbench column can be mapped onto. Free.\n\nClosed to `contact` / `company` because the handler indexes a dict with\nthis value directly - a free string would raise a KeyError inside and\nescape as a 500 instead of a 422 naming the two kinds.","operationId":"list_workbench_target_fields_workbench_target_fields_get","parameters":[{"name":"entity_type","in":"query","required":false,"schema":{"enum":["contact","company"],"type":"string","description":"Which record kind the fields are for.","default":"contact","title":"Entity Type"},"description":"Which record kind the fields are for."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/source-credentials":{"get":{"tags":["Workbench"],"summary":"List Workbench Source Credentials","description":"Every ingest credential in the organisation - owner, scope, expiry. Free.\n\nHashes and full secrets are NEVER returned; a credential's value is\nreadable only once, at the moment it is minted.\n\nGated on Workbench WRITE even though it reads, matching the app: the\norg-wide inventory names which person owns each credential, so it is a\ngovernance view rather than ordinary table data.","operationId":"list_workbench_source_credentials_workbench_source_credentials_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/rows/query":{"post":{"tags":["Workbench"],"summary":"Query Workbench Rows","description":"Read a window of rows with a filter and a sort. FREE - a read.\n\nPOST only because the filter is a structured body; nothing is written,\nenqueued or charged. `GET /workbench/tables/{id}/rows` is the simple form.","operationId":"query_workbench_rows_workbench_tables__table_id__rows_query_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StagingRowsQueryRequest","default":{"start_row":0,"end_row":100}}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/columns/{col_id}/sources":{"post":{"tags":["Workbench"],"summary":"Configure Workbench Column Source","description":"Point an ingest source at a column. Free.\n\nThe credential this mints is shown ONCE, in this response. There is no\nsecond read - `GET /workbench/source-credentials` lists metadata only.\n\n`rotate_existing` is an explicit acknowledgement rather than a default:\nrotating invalidates the current credential IMMEDIATELY, so anything\nalready posting with it stops at that instant.","operationId":"configure_workbench_column_source_workbench_tables__table_id__columns__col_id__sources_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"col_id","in":"path","required":true,"schema":{"type":"integer","description":"Column id.","title":"Col Id"},"description":"Column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ConfigureRawSourceRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"},"get":{"tags":["Workbench"],"summary":"List Workbench Column Sources","description":"The ingest sources bound to a raw JSON column, with their webhook paths.\nFree. Credentials are never returned.","operationId":"list_workbench_column_sources_workbench_tables__table_id__columns__col_id__sources_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"col_id","in":"path","required":true,"schema":{"type":"integer","description":"Column id.","title":"Col Id"},"description":"Column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/columns/{col_id}/sources/{source_type}":{"delete":{"tags":["Workbench"],"summary":"Revoke Workbench Column Source","description":"Revoke a column's ingest source. Free.\n\nAnything still posting with that credential starts failing immediately.\nRows already ingested are untouched.","operationId":"revoke_workbench_column_source_workbench_tables__table_id__columns__col_id__sources__source_type__delete","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"col_id","in":"path","required":true,"schema":{"type":"integer","description":"Column id.","title":"Col Id"},"description":"Column id."},{"name":"source_type","in":"path","required":true,"schema":{"type":"string","description":"Which source binding to revoke.","title":"Source Type"},"description":"Which source binding to revoke."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/regenerate-key":{"post":{"tags":["Workbench"],"summary":"Regenerate Workbench Key","description":"Mint the table's ingest credential. Free.\n\nTHE ONLY TIME THE KEY IS READABLE. It is returned here and never again -\nstore it on receipt. This is the credential the app's `X-Webhook-Key`\ningest path expects, which is why that path is not published here and does\nnot need to be.\n\n`rotate_existing` false mints only when there is none; true replaces the\ncurrent one and breaks anything still using it, immediately.","operationId":"regenerate_workbench_key_workbench_tables__table_id__regenerate_key_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RegenerateKeyRequest","default":{"rotate_existing":false}}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/discover-fields":{"post":{"tags":["Workbench"],"summary":"Discover Workbench Fields","description":"List the JSON paths present inside a raw column. FREE.\n\nDespite the name this calls no provider and spends nothing - it samples\nrows the customer already imported and reports the shapes it found. Call it\nbefore `columns/extract` to learn what `field_path` values exist.","operationId":"discover_workbench_fields_workbench_tables__table_id__discover_fields_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DiscoverFieldsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/columns/extract":{"post":{"tags":["Workbench"],"summary":"Extract Workbench Column","description":"Create a column from one JSON path, filled across every row. FREE.\n\n`field_path` comes from `discover-fields`. Pure local extraction: no\nprovider, no model, no credit.","operationId":"extract_workbench_column_workbench_tables__table_id__columns_extract_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ExtractColumnRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/columns/bulk-extract":{"post":{"tags":["Workbench"],"summary":"Bulk Extract Workbench Columns","description":"Up to 50 extractions in one pass. FREE.\n\nRead the per-extraction result rather than the HTTP status: one bad\n`field_path` is reported, not fatal to the other 49.","operationId":"bulk_extract_workbench_columns_workbench_tables__table_id__columns_bulk_extract_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BulkExtractRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/expand-array":{"post":{"tags":["Workbench"],"summary":"Expand Workbench Array","description":"Fan an array field out into one row per element. FREE.\n\nThis MULTIPLIES the row count: a table of 1,000 rows whose array averages\nten elements becomes 10,000 rows. Nothing is charged for the expansion\nitself, but every later per-row operation is then ten times the size.","operationId":"expand_workbench_array_workbench_tables__table_id__expand_array_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ExpandArrayRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/import/paste":{"post":{"tags":["Workbench"],"summary":"Paste Import Workbench Rows","description":"Import a rectangle of values directly. FREE.\n\nUp to 50,000 rows and 100 columns in one call. Missing columns are created\nfrom `headers`.\n\nIf the table has auto-enrichment ON, the rows this adds are enriched\nautomatically afterwards, and THAT spends credits. The import itself does\nnot.","operationId":"paste_import_workbench_rows_workbench_tables__table_id__import_paste_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PasteImportRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/import/datafile":{"post":{"tags":["Workbench"],"summary":"Import Workbench Datafile","description":"Import rows from an ALREADY-UPLOADED datafile. FREE.\n\nThis takes a `datafile_id`, never file content, which is why it fits a JSON\nenvelope. The upload that produces that id is a multipart operation and is\nnot part of this contract.\n\nSame auto-enrichment caveat as the paste import: the rows land free, and an\nauto-enriching table then spends on them.","operationId":"import_workbench_datafile_workbench_tables__table_id__import_datafile_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DatafileImportRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/locked-row-count":{"get":{"tags":["Workbench"],"summary":"Get Workbench Locked Row Count","description":"How many rows are still locked. FREE.\n\nAt one credit per row this number IS the price of unlocking everything.","operationId":"get_workbench_locked_row_count_workbench_tables__table_id__locked_row_count_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/unlock-quote":{"post":{"tags":["Workbench"],"summary":"Quote Workbench Unlock","description":"Price an unlock. CHARGES NOTHING, and unlocks nothing.\n\nReturns the exact locked-row count for the scope, the organisation's live\nbalance, and the shortfall if there is one. It also returns the\n`operation_id` that `unlock-rows` REQUIRES - so this call is not optional\nadvice, it is step one of the handshake.\n\nSend this exact body to `unlock-rows` afterwards: the quote prices the\nscope the unlock will charge for, and a different body is a different\nprice.","operationId":"quote_workbench_unlock_workbench_tables__table_id__unlock_quote_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UnlockStagingRowsRequest","default":{}}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/unlock-rows":{"post":{"tags":["Workbench"],"summary":"Unlock Workbench Rows","description":"Reveal masked contact details. SPENDS ONE CREDIT PER ROW.\n\nThis is the most expensive operation on the Workbench and the one a script\nis most likely to run by accident, because OMITTING `row_ids` UNLOCKS EVERY\nLOCKED ROW IN THE TABLE. A 10,000-row table costs 10,000 credits.\n\n`operation_id` is REQUIRED and comes from `unlock-quote`. It is what binds\nthe charge to a price the caller was shown, and it makes a retried unlock\nidempotent rather than charging twice for the same rows. Without it the\nrequest is refused.\n\nSet `approved_max_credits` as well: the run refuses to exceed it, which is\nthe difference between a bug costing you one request and costing you a\nbalance.","operationId":"unlock_workbench_rows_workbench_tables__table_id__unlock_rows_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UnlockStagingRowsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/find-people/configure":{"post":{"tags":["Workbench"],"summary":"Configure Workbench Find People","description":"Search for contacts at each company row. SPENDS CREDITS.\n\nThis queries the licensed people corpus and writes the matches into a\ncontact table. The rows land LOCKED: the search is what this costs, and\nrevealing each contact's details then costs a further credit per row\nthrough `unlock-rows`.\n\n`max_total_people` is the real cost control - it is a hard ceiling across\nevery company row, not a per-company hint. `broad_search_acknowledged` must\nbe set to run with NO filters, because an unfiltered search returns the\nwidest and most expensive possible result.","operationId":"configure_workbench_find_people_workbench_tables__table_id__find_people_configure_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ConfigureStagingFindPeopleRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/enrichment-configs":{"get":{"tags":["Workbench"],"summary":"List Workbench Enrichment Configs","description":"Every enrichment configuration attached to this table. FREE.\n\nThe inventory of what WOULD spend if run - read it before enabling\nauto-enrichment, which runs all of them.","operationId":"list_workbench_enrichment_configs_workbench_tables__table_id__enrichment_configs_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to one config kind. Omit for all of them.","title":"Type"},"description":"Narrow to one config kind. Omit for all of them."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/find-people/{config_id}":{"delete":{"tags":["Workbench"],"summary":"Delete Workbench Find People Config","description":"Remove a find-people configuration. Free. Contacts already found stay.","operationId":"delete_workbench_find_people_config_workbench_tables__table_id__find_people__config_id__delete","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"config_id","in":"path","required":true,"schema":{"type":"string","description":"Find-people configuration id (UUID).","title":"Config Id"},"description":"Find-people configuration id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/suggest-mappings":{"post":{"tags":["Workbench"],"summary":"Suggest Workbench Mappings","description":"Ask the model which source column maps to which target field. COSTS AN AI CALL.\n\nReturns a `job_id` immediately - the model call happens in the background.\nPoll `GET /workbench/tables/{id}/suggest-mappings/{job_id}` for the answer.\n\nThe suggestion is advisory: nothing is mapped until you write the mapping\nyourself.","operationId":"suggest_workbench_mappings_workbench_tables__table_id__suggest_mappings_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuggestMappingsRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/suggest-mappings/{job_id}":{"get":{"tags":["Workbench"],"summary":"Get Workbench Mapping Suggestion","description":"Collect a mapping suggestion. FREE - polling costs nothing.","operationId":"get_workbench_mapping_suggestion_workbench_tables__table_id__suggest_mappings__job_id__get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"job_id","in":"path","required":true,"schema":{"type":"string","description":"Job id returned by `suggest-mappings`.","title":"Job Id"},"description":"Job id returned by `suggest-mappings`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/columns/{col_id}/compute":{"post":{"tags":["Workbench"],"summary":"Compute Workbench Formula","description":"Evaluate a formula column across every row. FREE.\n\nThe formula runs locally - no model, no provider, no credit - so this is\nsafe to re-run as often as the inputs change. Per-row failures come back in\n`errors` rather than failing the call.","operationId":"compute_workbench_formula_workbench_tables__table_id__columns__col_id__compute_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"col_id","in":"path","required":true,"schema":{"type":"integer","description":"The formula column to evaluate.","title":"Col Id"},"description":"The formula column to evaluate."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/formula-columns":{"post":{"tags":["Workbench"],"summary":"Create Workbench Formula Columns","description":"Create a formula column with one child column per output. FREE.\n\nYou supply the formula, so nothing authors it and nothing is charged. The\nAI-authoring path is the one that costs, and\n`formula-columns/generate-quote` prices it.","operationId":"create_workbench_formula_columns_workbench_tables__table_id__formula_columns_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateFormulaColumnsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/formula-columns/generate-quote":{"get":{"tags":["Workbench"],"summary":"Quote Workbench Formula Generation","description":"Price AI formula authoring against the live balance. CHARGES NOTHING.\n\nDespite `generate` in the path this generates no formula and spends no\ncredit - it reports the fixed authoring charge, the organisation's balance,\nand whether the balance covers it.","operationId":"quote_workbench_formula_generation_workbench_tables__table_id__formula_columns_generate_quote_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/ai-presets":{"get":{"tags":["Workbench"],"summary":"List Workbench Ai Presets","description":"Every AI preset available to the organisation. FREE.\n\nThe catalogue of ready-made passes. `GET /workbench/tables/{id}/ai-presets`\nnarrows the same catalogue to the ones that fit a particular table's\ncolumns.","operationId":"list_workbench_ai_presets_workbench_ai_presets_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/ai-presets":{"get":{"tags":["Workbench"],"summary":"List Workbench Table Ai Presets","description":"The presets that can actually run on THIS table. FREE.\n\nFiltered by the columns the table has, so a preset listed here has its\ninputs satisfied. Selecting one still costs nothing until it is run.","operationId":"list_workbench_table_ai_presets_workbench_tables__table_id__ai_presets_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/ai/configure":{"post":{"tags":["Workbench"],"summary":"Configure Workbench Ai","description":"Set the table-level AI pass. FREE - saving runs nothing.\n\n`output_columns` decides which columns the pass writes into; they are\ncreated if missing. `multi_row_output` lets one source row produce up to\n`max_rows_per_source` rows, which multiplies what a later run costs.","operationId":"configure_workbench_ai_workbench_tables__table_id__ai_configure_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SaveStagingAIConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/ai/migrate-legacy":{"post":{"tags":["Workbench"],"summary":"Migrate Workbench Legacy Ai Config","description":"Move an old single-prompt config onto the group model. FREE.\n\nA one-off data migration for tables configured before AI groups existed.\nIt reshapes stored configuration and runs nothing.","operationId":"migrate_workbench_legacy_ai_config_workbench_tables__table_id__ai_migrate_legacy_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/ai/groups/config":{"post":{"tags":["Workbench"],"summary":"Create Workbench Ai Group","description":"Create an AI group on this table. FREE - saving never runs.\n\n`config.run_immediately` is pinned to false by the app, so this cannot\nbecome a spend by accident. Run the group explicitly afterwards.\n\nTwo settings decide most of what a later run costs:\n`config.skip_existing_values` (skip rows that already have a value) and\n`config.skip_recently_enriched` (skip rows touched in the last 30 days).\nBoth default to true; turning either off re-buys data you already have.\n\nThe path is `/ai/groups/config` rather than a POST to `/ai/groups`, matching\nthe app exactly - a different spelling here would be a second way to say the\nsame thing.","operationId":"create_workbench_ai_group_workbench_tables__table_id__ai_groups_config_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SaveAIConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/ai/groups/{group_id}":{"put":{"tags":["Workbench"],"summary":"Update Workbench Ai Group","description":"Replace a group's definition. FREE - editing runs nothing.\n\nA full replacement, not a patch: `config` is written as given, so read the\ngroup first and send it back changed rather than sending only the field you\nmeant to move.","operationId":"update_workbench_ai_group_workbench_tables__table_id__ai_groups__group_id__put","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"AI group id (starts with `ai_enrich`).","title":"Group Id"},"description":"AI group id (starts with `ai_enrich`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateAIConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Workbench"],"summary":"Delete Workbench Ai Group","description":"Remove an AI group. Free.\n\nValues the group already wrote into columns stay - you are deleting the\ninstruction, not the data you paid for.","operationId":"delete_workbench_ai_group_workbench_tables__table_id__ai_groups__group_id__delete","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"AI group id (starts with `ai_enrich`).","title":"Group Id"},"description":"AI group id (starts with `ai_enrich`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"},"get":{"tags":["Workbench"],"summary":"Get Workbench Ai Group","description":"Read one AI group's configuration. Free.","operationId":"get_workbench_ai_group_workbench_tables__table_id__ai_groups__group_id__get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"The AI group id.","title":"Group Id"},"description":"The AI group id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/columns/{col_id}/ai-config":{"put":{"tags":["Workbench"],"summary":"Save Workbench Column Ai Config","description":"Set ONE column's AI pass. FREE - saving runs nothing.\n\n`conditions` is the per-row gate: rows that do not match are skipped by a\nlater run and cost nothing, which is the cheapest way to narrow a pass.\n\n`usecase` is closed to the two the app accepts, because the value reaches a\npattern check and a pricing table inside - an invented usecase would either\n422 opaquely or price against the wrong tariff.","operationId":"save_workbench_column_ai_config_workbench_tables__table_id__columns__col_id__ai_config_put","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"col_id","in":"path","required":true,"schema":{"type":"integer","description":"Column id.","title":"Col Id"},"description":"Column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SaveColumnAIConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"},"get":{"tags":["Workbench"],"summary":"Get Workbench Column Ai Config","description":"Read one column's AI pass. FREE.","operationId":"get_workbench_column_ai_config_workbench_tables__table_id__columns__col_id__ai_config_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"col_id","in":"path","required":true,"schema":{"type":"integer","description":"Column id.","title":"Col Id"},"description":"Column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/ai/groups/{group_id}/find-people/review":{"get":{"tags":["Workbench"],"summary":"Review Workbench Find People Candidates","description":"Contacts a find-people group turned up and is holding for review. FREE.\n\nOnly populated when the group's `export_mode` is `review`. Under `auto`\nthere is nothing to review because the contacts were already exported.","operationId":"review_workbench_find_people_candidates_workbench_tables__table_id__ai_groups__group_id__find_people_review_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"AI group id (starts with `ai_enrich`).","title":"Group Id"},"description":"AI group id (starts with `ai_enrich`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/ai/groups/{group_id}/find-people/skip":{"post":{"tags":["Workbench"],"summary":"Skip Workbench Find People Candidates","description":"Reject candidates from the review queue. FREE.\n\nMarks them skipped so they are not exported. The search that found them has\nalready been paid for; skipping does not refund it, it just stops them\nreaching a list.","operationId":"skip_workbench_find_people_candidates_workbench_tables__table_id__ai_groups__group_id__find_people_skip_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"AI group id (starts with `ai_enrich`).","title":"Group Id"},"description":"AI group id (starts with `ai_enrich`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateStagingAIFindPeopleCandidatesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/ai/generate-prompt":{"post":{"tags":["Workbench"],"summary":"Generate Workbench Prompt","description":"Draft an AI prompt from this table's columns. COSTS AN AI CALL.\n\nA model reads the column names and five sample rows and writes a prompt for\nyou. It does not debit the credit balance, but it is a real model call, so\nit is not free to run in a loop.\n\nThe returned prompt is a draft: nothing is configured and nothing is\nenriched until you save it.","operationId":"generate_workbench_prompt_workbench_tables__table_id__ai_generate_prompt_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StagingPromptGeneratorRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/auto-enrich":{"put":{"tags":["Workbench"],"summary":"Set Workbench Auto Enrich","description":"Enrich every row that arrives, automatically. STARTS ONGOING SPEND.\n\nThe PUT itself charges nothing. What it does is remove the human from the\nloop: from the moment this is on, every row that lands in the table - from\nan import, a webhook, a scraper or a routing rule - is enriched by the\nconfigured AI passes WITHOUT a further API call, and each one costs.\n\nThat is why this is graded as a spend rather than an ordinary setting. It\nis the single switch on this surface most likely to produce a bill nobody\nasked for, so `enabled` is explicit rather than a toggle: a retried request\ncannot silently turn it back on.\n\nRead `GET /workbench/tables/{id}/enrichment-configs` first - that is the\nlist of passes this will start running.","operationId":"set_workbench_auto_enrich_workbench_tables__table_id__auto_enrich_put","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ToggleAutoEnrichRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/ai/run-all":{"post":{"tags":["Workbench"],"summary":"Run Workbench Ai","description":"Run every configured AI pass over the table. SPENDS CREDITS.\n\nOMITTING `row_ids` RUNS EVERY ROW, and the body is optional - so a bare\n`POST` with no body at all is \"enrich this entire table\". On a 10,000-row\ntable with three configured columns that is 30,000 model calls.\n\nSet `approved_max_credits`. The run refuses to exceed it, and a credit\npreflight happens before any work starts, so an over-budget request costs\nnothing rather than costing until the balance runs out.\n\nReturns 202 and a handle: the work happens in the background. The group's\n`skip_existing_values` and `skip_recently_enriched` settings still apply,\nso re-running is usually far cheaper than the first pass.","operationId":"run_workbench_ai_workbench_tables__table_id__ai_run_all_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RunStagingAIRequest","default":{"qualification_mode":false}}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/schedule":{"put":{"tags":["Workbench"],"summary":"Set Workbench Schedule","description":"Run something on this table on a schedule. CAN ARM ONGOING SPEND.\n\n`action_type: run_ai` means every firing runs the table's AI passes and\ncharges for them - nightly, forever, with nobody in the loop. `run_formula`\nis local and free; `crm_import` reaches the customer's CRM.\n\n`enabled` defaults to FALSE, so writing a schedule and starting it are two\nseparate acts. That is deliberate: it lets a caller define the cadence,\nread it back, and only then turn it on.","operationId":"set_workbench_schedule_workbench_tables__table_id__schedule_put","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ScheduleConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"},"get":{"tags":["Workbench"],"summary":"Get Workbench Schedule","description":"Read the table's schedule. FREE.\n\nWorth reading before an audit of where credit is going: a schedule is the\none spend on this surface that nobody triggers by hand.","operationId":"get_workbench_schedule_workbench_tables__table_id__schedule_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Workbench"],"summary":"Delete Workbench Schedule","description":"Remove the schedule. Free, and the fastest way to stop recurring spend.","operationId":"delete_workbench_schedule_workbench_tables__table_id__schedule_delete","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/triggers/{trigger_id}":{"put":{"tags":["Workbench"],"summary":"Update Workbench Trigger","description":"Edit an automation trigger. CAN ARM ONGOING SPEND.\n\nA PATCH in spirit: omitted fields are left alone. `enabled` true on a\ntrigger whose action is an AI pass means each matching row is enriched -\nand charged - as it arrives.","operationId":"update_workbench_trigger_workbench_tables__table_id__triggers__trigger_id__put","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"trigger_id","in":"path","required":true,"schema":{"type":"integer","description":"Trigger id.","title":"Trigger Id"},"description":"Trigger id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateTriggerRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Workbench"],"summary":"Delete Workbench Trigger","description":"Delete a trigger. Stops whatever spend it armed.","operationId":"delete_workbench_trigger_workbench_tables__table_id__triggers__trigger_id__delete","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"trigger_id","in":"path","required":true,"schema":{"type":"integer","description":"Trigger id.","title":"Trigger Id"},"description":"Trigger id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/import/crm":{"post":{"tags":["Workbench"],"summary":"Import Workbench From Crm","description":"Pull records out of a connected CRM into this table. READS THEIR SYSTEM.\n\nNo credit is charged for the import itself, but it reaches into the\ncustomer's own CRM, which is why it needs the same grant as the other\noperations that do - a customer can hand out \"read my workbench\" without\nhanding out \"read my Salesforce\".\n\n`limit` caps what lands, and it matters twice: once for the CRM's own API\nquota, and again if this table auto-enriches, because every imported row is\nthen a row that spends.\n\n`crm_provider` and `object_type` are the app's legacy aliases for\n`provider_type` and `entity_type`. They are mirrored because the app still\naccepts them, not because new code should send them.","operationId":"import_workbench_from_crm_workbench_tables__table_id__import_crm_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CRMImportRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/send-to-sequence":{"post":{"tags":["Workbench"],"summary":"Send Workbench Rows To Sequence","description":"Enrol workbench rows into a sequence. THIS EMAILS REAL PEOPLE.\n\nThe rows stop being scratch data at this point: a sequence sends on its own\nschedule, to the addresses in these rows, from the organisation's mailboxes.\nThere is no preview step here, and nothing to undo once a message is out.\n\nOMITTING `row_ids` SENDS EVERY ROW IN THE TABLE, including rows that are\nstill locked or half-enriched. Name the rows.","operationId":"send_workbench_rows_to_sequence_workbench_tables__table_id__send_to_sequence_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SendToSequenceRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench/scraper/presets":{"get":{"tags":["Workbench"],"summary":"List Workbench Scraper Presets","description":"The scraper presets available, with their per-result rates. FREE.\n\nRead the rate here, then price a specific run with `credit-estimate`.","operationId":"list_workbench_scraper_presets_workbench_scraper_presets_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/scraper/providers/{provider}/check-token":{"get":{"tags":["Workbench"],"summary":"Check Workbench Scraper Token","description":"Is the organisation's scraper credential present and working? FREE.\n\nA connectivity check against the provider, not a scrape. Call it before a\nrun so a missing credential fails here rather than halfway through.\n\n`provider` is a path parameter rather than a literal segment, matching\n`/crm-syncs/{provider}/status`. Today it resolves to the one connected\nprovider the app supports; the handler takes no provider argument, so the\nvalue selects the route rather than being forwarded.","operationId":"check_workbench_scraper_token_workbench_scraper_providers__provider__check_token_get","parameters":[{"name":"provider","in":"path","required":true,"schema":{"const":"apify","type":"string","description":"Which connected scraper provider.","title":"Provider"},"description":"Which connected scraper provider."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/scraper/credit-estimate":{"get":{"tags":["Workbench"],"summary":"Estimate Workbench Scraper Credits","description":"Price a built-in scraper run. CHARGES NOTHING.\n\nA worst-case quote: what `max_results` rows would cost, plus the\npost-scrape enrichment when `auto_enrich` is set, against the live balance.\nNothing is scraped and no credit moves.\n\nThe estimate and the run share one costing function on purpose, so the\nnumber quoted here is the number the run's own credit gate enforces.","operationId":"estimate_workbench_scraper_credits_workbench_scraper_credit_estimate_get","parameters":[{"name":"table_id","in":"query","required":true,"schema":{"type":"string","description":"The table the results would land in.","title":"Table Id"},"description":"The table the results would land in."},{"name":"max_results","in":"query","required":true,"schema":{"type":"integer","description":"Ceiling on results the run would return.","title":"Max Results"},"description":"Ceiling on results the run would return."},{"name":"auto_enrich","in":"query","required":false,"schema":{"type":"boolean","description":"Price the post-scrape enrichment too. Leave false and the quote covers the scrape ALONE - which is the number people misread.","default":false,"title":"Auto Enrich"},"description":"Price the post-scrape enrichment too. Leave false and the quote covers the scrape ALONE - which is the number people misread."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/scraper/providers/{provider}/credit-estimate":{"get":{"tags":["Workbench"],"summary":"Estimate Workbench Provider Scraper Credits","description":"Price a run on a connected scraper provider. CHARGES NOTHING.\n\nEvery component broken out: the scraper credits, the per-result rate, the\npost-scrape enrichment, the live balance and what would be left. Nothing is\nscraped.","operationId":"estimate_workbench_provider_scraper_credits_workbench_scraper_providers__provider__credit_estimate_get","parameters":[{"name":"provider","in":"path","required":true,"schema":{"const":"apify","type":"string","description":"Which connected scraper provider.","title":"Provider"},"description":"Which connected scraper provider."},{"name":"table_id","in":"query","required":true,"schema":{"type":"string","description":"The table the results would land in.","title":"Table Id"},"description":"The table the results would land in."},{"name":"max_results","in":"query","required":true,"schema":{"type":"integer","description":"Ceiling on results the run would return.","title":"Max Results"},"description":"Ceiling on results the run would return."},{"name":"preset_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Preset to price against. Omit for the provider's default rate.","title":"Preset Id"},"description":"Preset to price against. Omit for the provider's default rate."},{"name":"auto_enrich","in":"query","required":false,"schema":{"type":"boolean","description":"Price the post-scrape enrichment too.","default":false,"title":"Auto Enrich"},"description":"Price the post-scrape enrichment too."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/ai/validate-credits":{"post":{"tags":["Workbench"],"summary":"Quote Workbench Ai Run","description":"Price an AI run before starting it. FREE.\n\nName the run you are about to start: `group_id`, `column_id`, or\n`all_columns`; none prices the table's default AI pass. Pass the answer's\n`required_credits` to the run as `approved_max_credits`.","operationId":"quote_workbench_ai_run_workbench_tables__table_id__ai_validate_credits_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/WorkbenchCreditValidationRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/ai/run":{"post":{"tags":["Workbench"],"summary":"Run Workbench Default Ai","description":"Run the table's default AI pass. CHARGES per row.\n\nOMITTING `row_ids` RUNS EVERY PENDING ROW. Quote it first with\n`POST .../ai/validate-credits`.","operationId":"run_workbench_default_ai_workbench_tables__table_id__ai_run_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/RunStagingAIRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/ai/preview":{"post":{"tags":["Workbench"],"summary":"Preview Workbench Ai","description":"Run the default AI pass on the first three pending rows. CHARGES.\n\nA preview in scope, not in price: it is the real pass and bills those rows.\nOnly `approved_max_credits` and `quote_expires_at` are read from the body.","operationId":"preview_workbench_ai_workbench_tables__table_id__ai_preview_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/RunStagingAIRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/ai/groups/{group_id}/run":{"post":{"tags":["Workbench"],"summary":"Run Workbench Ai Group","description":"Run one saved AI group. CHARGES per row.\n\nOMITTING `row_ids` RUNS EVERY PENDING ROW. Quote it with\n`POST .../ai/validate-credits` and `group_id`.","operationId":"run_workbench_ai_group_workbench_tables__table_id__ai_groups__group_id__run_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"The AI group id.","title":"Group Id"},"description":"The AI group id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/RunStagingAIRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/columns/{col_id}/ai/run":{"post":{"tags":["Workbench"],"summary":"Run Workbench Column Ai","description":"Run one column's AI. CHARGES per row.\n\nOMITTING `row_ids` RUNS EVERY ROW. Quote it with\n`POST .../ai/validate-credits` and `column_id`.","operationId":"run_workbench_column_ai_workbench_tables__table_id__columns__col_id__ai_run_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"col_id","in":"path","required":true,"schema":{"type":"integer","description":"Column id.","title":"Col Id"},"description":"Column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/RunStagingAIRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/ai/groups/{group_id}/find-people/rows/{source_row_id}":{"get":{"tags":["Workbench"],"summary":"Get Workbench Ai Find People Row","description":"The people an AI find-people group found for one row. Free.","operationId":"get_workbench_ai_find_people_row_workbench_tables__table_id__ai_groups__group_id__find_people_rows__source_row_id__get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"The AI group id.","title":"Group Id"},"description":"The AI group id."},{"name":"source_row_id","in":"path","required":true,"schema":{"type":"integer","description":"The company row the candidates were found for.","title":"Source Row Id"},"description":"The company row the candidates were found for."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/ai/groups/{group_id}/find-people/export":{"post":{"tags":["Workbench"],"summary":"Export Workbench Ai Find People","description":"Copy chosen candidates into the group's people table. Free.","operationId":"export_workbench_ai_find_people_workbench_tables__table_id__ai_groups__group_id__find_people_export_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"The AI group id.","title":"Group Id"},"description":"The AI group id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateStagingAIFindPeopleCandidatesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/waterfall/configs":{"post":{"tags":["Workbench"],"summary":"Save Workbench Waterfall","description":"Create a waterfall column, or overwrite one when `config.column_id` names\nan existing column. Free: saving never runs it.","operationId":"save_workbench_waterfall_workbench_tables__table_id__waterfall_configs_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SaveWaterfallRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/waterfall/configs/{column_id}":{"get":{"tags":["Workbench"],"summary":"Get Workbench Waterfall","description":"Read a waterfall column's steps and settings. Free.","operationId":"get_workbench_waterfall_workbench_tables__table_id__waterfall_configs__column_id__get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"column_id","in":"path","required":true,"schema":{"type":"integer","description":"The waterfall column id.","title":"Column Id"},"description":"The waterfall column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"},"put":{"tags":["Workbench"],"summary":"Update Workbench Waterfall","description":"Replace a waterfall column's steps and settings. Free: editing runs nothing.","operationId":"update_workbench_waterfall_workbench_tables__table_id__waterfall_configs__column_id__put","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"column_id","in":"path","required":true,"schema":{"type":"integer","description":"The waterfall column id.","title":"Column Id"},"description":"The waterfall column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateWaterfallConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/waterfall/configs/{column_id}/validate-credits":{"post":{"tags":["Workbench"],"summary":"Quote Workbench Waterfall Run","description":"Price a waterfall run. FREE. OMITTING `row_ids` prices EVERY row.","operationId":"quote_workbench_waterfall_run_workbench_tables__table_id__waterfall_configs__column_id__validate_credits_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"column_id","in":"path","required":true,"schema":{"type":"integer","description":"The waterfall column id.","title":"Column Id"},"description":"The waterfall column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/WorkbenchCreditValidationRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/waterfall/configs/{column_id}/run":{"post":{"tags":["Workbench"],"summary":"Run Workbench Waterfall","description":"Run a waterfall column. CHARGES per provider call.\n\nOMITTING `row_ids` RUNS EVERY ELIGIBLE ROW. Refused (402) without enough\ncredit; quote it first with `.../validate-credits`.","operationId":"run_workbench_waterfall_workbench_tables__table_id__waterfall_configs__column_id__run_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"column_id","in":"path","required":true,"schema":{"type":"integer","description":"The waterfall column id.","title":"Column Id"},"description":"The waterfall column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/RunStagingAIRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/rows/{row_id}":{"get":{"tags":["Workbench"],"summary":"Get Workbench Row","description":"Read one row. Free.","operationId":"get_workbench_row_workbench_tables__table_id__rows__row_id__get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"row_id","in":"path","required":true,"schema":{"type":"integer","description":"Row id.","title":"Row Id"},"description":"Row id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Workbench"],"summary":"Update Workbench Row","description":"Set ONE field on one row - the grid's cell edit.\n\nOne field per call, matching the app. A whole-row PUT would make a\nconcurrent edit to a different cell silently lose.","operationId":"update_workbench_row_workbench_tables__table_id__rows__row_id__patch","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Table id (UUID).","title":"Table Id"},"description":"Table id (UUID)."},{"name":"row_id","in":"path","required":true,"schema":{"type":"integer","description":"Row id.","title":"Row Id"},"description":"Row id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkbenchRowUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/import/search/preview":{"post":{"tags":["Workbench"],"summary":"Preview Workbench Search Import","description":"Sample what a people search would import, and how many it matches. Free.\n\nContact details stay masked; nothing is imported.","operationId":"preview_workbench_search_import_workbench_tables__table_id__import_search_preview_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SearchImportPreviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/import/search/research/preview":{"post":{"tags":["Workbench"],"summary":"Preview Workbench Research Import","description":"Describe your leads in words; a model writes the search and returns a\nsample. CHARGES for the model call. Nothing is imported.","operationId":"preview_workbench_research_import_workbench_tables__table_id__import_search_research_preview_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SearchResearchPreviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/import/search":{"post":{"tags":["Workbench"],"summary":"Import Workbench From Search","description":"Import people from a search into the table. CHARGES when revealed.\n\nUp to `limit` rows land LOCKED: each costs a credit to unlock with\n`POST .../unlock-rows`. Sample it first with `.../import/search/preview`.","operationId":"import_workbench_from_search_workbench_tables__table_id__import_search_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkbenchSearchImportRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/find-people/configs":{"get":{"tags":["Workbench"],"summary":"List Workbench Find People Configs","description":"The table's find-people configurations. Free.","operationId":"list_workbench_find_people_configs_workbench_tables__table_id__find_people_configs_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/find-people/{config_id}/run":{"post":{"tags":["Workbench"],"summary":"Run Workbench Find People","description":"Find people at the table's companies. CHARGES per company searched.\n\n`all_rows` (the default) searches EVERY company row; `first_10` is a cheap\ntrial; `selected` needs `row_ids` or `exclude_row_ids`.","operationId":"run_workbench_find_people_workbench_tables__table_id__find_people__config_id__run_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"config_id","in":"path","required":true,"schema":{"type":"string","description":"Find-people configuration id (UUID).","title":"Config Id"},"description":"Find-people configuration id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RunWorkbenchFindPeopleRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/find-people/{config_id}/contacts":{"get":{"tags":["Workbench"],"summary":"List Workbench Find People Contacts","description":"The people a find-people run found for one company row. Free.","operationId":"list_workbench_find_people_contacts_workbench_tables__table_id__find_people__config_id__contacts_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"config_id","in":"path","required":true,"schema":{"type":"string","description":"Find-people configuration id (UUID).","title":"Config Id"},"description":"Find-people configuration id (UUID)."},{"name":"source_row_id","in":"query","required":true,"schema":{"type":"integer","description":"The company row.","title":"Source Row Id"},"description":"The company row."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":100,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/triggers":{"post":{"tags":["Workbench"],"summary":"Create Workbench Trigger","description":"React to rows as they arrive or change. CAN ARM ONGOING SPEND.\n\n`enabled` DEFAULTS TO TRUE. With `action_type: run_ai`, every matching row\nis enriched, and charged, as it arrives. `webhook_notify` URLs are checked\nand unsafe targets refused.","operationId":"create_workbench_trigger_workbench_tables__table_id__triggers_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateTriggerRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"},"get":{"tags":["Workbench"],"summary":"List Workbench Triggers","description":"The table's triggers. Free.","operationId":"list_workbench_triggers_workbench_tables__table_id__triggers_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/pipelines":{"post":{"tags":["Workbench"],"summary":"Create Workbench Pipeline","description":"Create a pipeline that processes new rows step by step. CAN ARM SPEND.\n\n`enabled` defaults to false. Enabled, it runs its AI and waterfall steps -\neach charged per row - on every row that arrives.","operationId":"create_workbench_pipeline_workbench_tables__table_id__pipelines_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateWorkbenchPipelineRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"},"get":{"tags":["Workbench"],"summary":"List Workbench Pipelines","description":"The table's pipelines. Free.","operationId":"list_workbench_pipelines_workbench_tables__table_id__pipelines_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/pipelines/{pipeline_id}":{"get":{"tags":["Workbench"],"summary":"Get Workbench Pipeline","description":"Read one pipeline. Free.","operationId":"get_workbench_pipeline_workbench_tables__table_id__pipelines__pipeline_id__get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","description":"Pipeline id (UUID).","title":"Pipeline Id"},"description":"Pipeline id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"},"put":{"tags":["Workbench"],"summary":"Update Workbench Pipeline","description":"Edit a pipeline; omitted fields are left alone. CAN ARM SPEND when\n`enabled` is true.","operationId":"update_workbench_pipeline_workbench_tables__table_id__pipelines__pipeline_id__put","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","description":"Pipeline id (UUID).","title":"Pipeline Id"},"description":"Pipeline id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateWorkbenchPipelineRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Workbench"],"summary":"Delete Workbench Pipeline","description":"Delete a pipeline.","operationId":"delete_workbench_pipeline_workbench_tables__table_id__pipelines__pipeline_id__delete","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","description":"Pipeline id (UUID).","title":"Pipeline Id"},"description":"Pipeline id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/analytics":{"get":{"tags":["Workbench"],"summary":"Get Workbench Analytics","description":"Row status distribution, row counts and column fill rates. Free.","operationId":"get_workbench_analytics_workbench_tables__table_id__analytics_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/history":{"get":{"tags":["Workbench"],"summary":"Get Workbench History","description":"What has run on this table - imports, AI passes, exports - newest first.\nFree. Redacted: no credentials and no row data.","operationId":"get_workbench_history_workbench_tables__table_id__history_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":25,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/connections":{"post":{"tags":["Workbench"],"summary":"Create Workbench Connection","description":"Connect this table to another table in your organisation, so rows are\ncopied across. Free.","operationId":"create_workbench_connection_workbench_tables__table_id__connections_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TableConnectionRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"},"get":{"tags":["Workbench"],"summary":"List Workbench Connections","description":"Connections where this table is the source or the destination. Free.","operationId":"list_workbench_connections_workbench_tables__table_id__connections_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/connections/{connection_id}":{"delete":{"tags":["Workbench"],"summary":"Delete Workbench Connection","description":"Remove a connection. Rows already copied stay where they are.","operationId":"delete_workbench_connection_workbench_tables__table_id__connections__connection_id__delete","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"connection_id","in":"path","required":true,"schema":{"type":"integer","description":"Connection id.","title":"Connection Id"},"description":"Connection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/connections/{connection_id}/sync":{"post":{"tags":["Workbench"],"summary":"Sync Workbench Connection","description":"Copy rows across a connection now. Free; stays inside your organisation.","operationId":"sync_workbench_connection_workbench_tables__table_id__connections__connection_id__sync_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"connection_id","in":"path","required":true,"schema":{"type":"integer","description":"Connection id.","title":"Connection Id"},"description":"Connection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/scraper/runs":{"post":{"tags":["Workbench"],"summary":"Run Workbench Scraper","description":"Describe what to collect and the scraper fills the table. CHARGES per\nresult, plus enrichment of each when `auto_enrich` is true.\n\nQuote it first with `GET /workbench/scraper/credit-estimate` and pass the\napproved amount as `approved_max_credits` with `quote_expires_at`.","operationId":"run_workbench_scraper_workbench_tables__table_id__scraper_runs_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RunBuiltinScraperRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"},"get":{"tags":["Workbench"],"summary":"List Workbench Scraper Runs","description":"The table's scraper runs, newest first, with a total. Free.","operationId":"list_workbench_scraper_runs_workbench_tables__table_id__scraper_runs_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":20,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/scraper/providers/{provider}/runs":{"post":{"tags":["Workbench"],"summary":"Run Workbench Provider Scraper","description":"Run a scraper on your connected provider account. CHARGES per result.\n\n`auto_enrich` DEFAULTS TO TRUE: every result is also enriched and charged\nunless you turn it off. Quote it with\n`GET /workbench/scraper/providers/{provider}/credit-estimate`.","operationId":"run_workbench_provider_scraper_workbench_tables__table_id__scraper_providers__provider__runs_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"provider","in":"path","required":true,"schema":{"const":"apify","type":"string","description":"Which scraper provider.","title":"Provider"},"description":"Which scraper provider."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RunProviderScraperRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/scraper/runs/{run_id}":{"get":{"tags":["Workbench"],"summary":"Get Workbench Scraper Run","description":"One scraper run, with live progress while it is running. Free.","operationId":"get_workbench_scraper_run_workbench_tables__table_id__scraper_runs__run_id__get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Workbench table id (UUID).","title":"Table Id"},"description":"Workbench table id (UUID)."},{"name":"run_id","in":"path","required":true,"schema":{"type":"string","description":"Scraper run id (UUID).","title":"Run Id"},"description":"Scraper run id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/scraper/providers/{provider}/connection":{"get":{"tags":["Workbench"],"summary":"Get Scraper Provider Connection","description":"Whether your provider account is connected. Free. The token is never returned.","operationId":"get_scraper_provider_connection_workbench_scraper_providers__provider__connection_get","parameters":[{"name":"provider","in":"path","required":true,"schema":{"const":"apify","type":"string","description":"Which scraper provider.","title":"Provider"},"description":"Which scraper provider."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"},"put":{"tags":["Workbench"],"summary":"Save Scraper Provider Connection","description":"Connect, or replace, your provider account token. Free.\n\nThe token is sealed at rest and never returned. Check it first with\n`POST .../connection/test`; saving does not.","operationId":"save_scraper_provider_connection_workbench_scraper_providers__provider__connection_put","parameters":[{"name":"provider","in":"path","required":true,"schema":{"const":"apify","type":"string","description":"Which scraper provider.","title":"Provider"},"description":"Which scraper provider."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ScraperConnectionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Workbench"],"summary":"Delete Scraper Provider Connection","description":"Disconnect your provider account. Provider scraper runs stop working.","operationId":"delete_scraper_provider_connection_workbench_scraper_providers__provider__connection_delete","parameters":[{"name":"provider","in":"path","required":true,"schema":{"const":"apify","type":"string","description":"Which scraper provider.","title":"Provider"},"description":"Which scraper provider."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/workbench/scraper/providers/{provider}/connection/test":{"post":{"tags":["Workbench"],"summary":"Test Scraper Provider Connection","description":"Check a token against the provider without saving it. Contacts the\nprovider; free. Answers `success: false` with a reason rather than an error.","operationId":"test_scraper_provider_connection_workbench_scraper_providers__provider__connection_test_post","parameters":[{"name":"provider","in":"path","required":true,"schema":{"const":"apify","type":"string","description":"Which scraper provider.","title":"Provider"},"description":"Which scraper provider."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ScraperConnectionTestRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/workbench-bindings":{"post":{"tags":["Workbench"],"summary":"Create Workbench Bindings","description":"Show a workflow's outputs as columns on a list. FREE.\n\nRequires WRITE access to the list. The columns appear on the list's next\ncolumn fetch; their values fill in when the workflow runs.","operationId":"create_workbench_bindings_workbench_bindings_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateWorkbenchBindingsRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"},"get":{"tags":["Workbench"],"summary":"List Workbench Bindings","description":"The workflow bindings on one list. FREE. Requires read access to it.","operationId":"list_workbench_bindings_workbench_bindings_get","parameters":[{"name":"list_id","in":"query","required":true,"schema":{"type":"integer","description":"The list whose bindings to read.","title":"List Id"},"description":"The list whose bindings to read."},{"name":"workflow_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only this workflow's bindings.","title":"Workflow Id"},"description":"Only this workflow's bindings."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench-bindings/{binding_id}":{"delete":{"tags":["Workbench"],"summary":"Delete Workbench Binding","description":"Remove one binding. FREE.\n\nThe column leaves the grid on the next column fetch. Requires WRITE access\nto the list the binding sits on; the app resolves that list from the\nbinding itself, so a binding on a list the key cannot write is refused.","operationId":"delete_workbench_binding_workbench_bindings__binding_id__delete","parameters":[{"name":"binding_id","in":"path","required":true,"schema":{"type":"string","description":"The binding to remove.","title":"Binding Id"},"description":"The binding to remove."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_EnrichmentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/workbench/tables":{"post":{"tags":["Workbench"],"summary":"Create Workbench Table","description":"Create an empty table.\n\n`entity_type` decides what the rows become on export and is settable here,\nat creation - which is why the update model does not offer it.","operationId":"create_workbench_table_workbench_tables_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkbenchTableCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkbenchTable_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"},"get":{"tags":["Workbench"],"summary":"List Workbench Tables","description":"This org's tables.","operationId":"list_workbench_tables_workbench_tables_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":20,"title":"Limit"}},{"name":"sort_field","in":"query","required":false,"schema":{"type":"string","default":"created_at","title":"Sort Field"}},{"name":"sort_order","in":"query","required":false,"schema":{"type":"string","default":"desc","title":"Sort Order"}},{"name":"filter_name","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Substring match on the table name.","title":"Filter Name"},"description":"Substring match on the table name."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkbenchTableList_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}":{"get":{"tags":["Workbench"],"summary":"Get Workbench Table","description":"One table's definition. Ungated, matching the app.","operationId":"get_workbench_table_workbench_tables__table_id__get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Table id (UUID).","title":"Table Id"},"description":"Table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkbenchTable_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"},"put":{"tags":["Workbench"],"summary":"Update Workbench Table","description":"Rename or re-describe. `entity_type` is fixed at creation.","operationId":"update_workbench_table_workbench_tables__table_id__put","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Table id (UUID).","title":"Table Id"},"description":"Table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkbenchTableUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Workbench"],"summary":"Delete Workbench Table","description":"Delete the table AND every row in it. Not recoverable through this API.","operationId":"delete_workbench_table_workbench_tables__table_id__delete","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Table id (UUID).","title":"Table Id"},"description":"Table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/rows":{"get":{"tags":["Workbench"],"summary":"List Workbench Rows","description":"A window of rows.\n\nPaged by `start_row`/`end_row`, not page/limit - this is a grid viewport,\nand translating it into pages would lose the ability to fetch an arbitrary\nwindow as a user scrolls.","operationId":"list_workbench_rows_workbench_tables__table_id__rows_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Table id (UUID).","title":"Table Id"},"description":"Table id (UUID)."},{"name":"start_row","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Start Row"}},{"name":"end_row","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":100,"title":"End Row"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkbenchPage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"},"post":{"tags":["Workbench"],"summary":"Add Workbench Row","description":"Add one row. `data` is keyed by column MACHINE name, not display name.","operationId":"add_workbench_row_workbench_tables__table_id__rows_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Table id (UUID).","title":"Table Id"},"description":"Table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkbenchRowCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/rows/bulk-delete":{"post":{"tags":["Workbench"],"summary":"Bulk Delete Workbench Rows","description":"Delete rows by id, or everything EXCEPT a set.\n\n`select_all` must be sent explicitly to delete everything. An empty\nselection is rejected rather than treated as a delete-all - the app's own\ncomment records why: \"a client bug can never turn 'nothing selected' into\n'delete the whole table'\".","operationId":"bulk_delete_workbench_rows_workbench_tables__table_id__rows_bulk_delete_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Table id (UUID).","title":"Table Id"},"description":"Table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkbenchRowsDeleteRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/columns":{"get":{"tags":["Workbench"],"summary":"List Workbench Columns","description":"The table's columns. Read this before writing rows - `data` keys are\ncolumn MACHINE names.","operationId":"list_workbench_columns_workbench_tables__table_id__columns_get","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Table id (UUID).","title":"Table Id"},"description":"Table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkbenchPage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"},"post":{"tags":["Workbench"],"summary":"Add Workbench Column","description":"Add a column.\n\n`name` is the machine name rows are keyed by and is constrained to\n`^[a-z][a-z0-9_]*$`; `display_name` is free text. Getting those the wrong\nway round produces a column nothing can address.","operationId":"add_workbench_column_workbench_tables__table_id__columns_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Table id (UUID).","title":"Table Id"},"description":"Table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkbenchColumnCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/columns/{column_id}":{"delete":{"tags":["Workbench"],"summary":"Delete Workbench Column","description":"Delete a column and the values in it, on every row.","operationId":"delete_workbench_column_workbench_tables__table_id__columns__column_id__delete","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Table id (UUID).","title":"Table Id"},"description":"Table id (UUID)."},{"name":"column_id","in":"path","required":true,"schema":{"type":"integer","description":"Column id.","title":"Column Id"},"description":"Column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/columns/{column_id}/mapping":{"put":{"tags":["Workbench"],"summary":"Map Workbench Column","description":"Point a column at a CRM field so export knows where its values go.\n\nSend `mapping_target: null` to clear it - an unmapped column is a real\nstate, not a missing argument.","operationId":"map_workbench_column_workbench_tables__table_id__columns__column_id__mapping_put","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Table id (UUID).","title":"Table Id"},"description":"Table id (UUID)."},{"name":"column_id","in":"path","required":true,"schema":{"type":"integer","description":"Column id.","title":"Column Id"},"description":"Column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkbenchColumnMappingRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/workbench/tables/{table_id}/export":{"post":{"tags":["Workbench"],"summary":"Export Workbench Table","description":"Export rows into an audience list. THIS CREATES REAL CRM RECORDS.\n\nA destination is REQUIRED - either `list_id`, or `create_new_list` with a\n`new_list_name`. The app would otherwise accept a body naming neither and\ndecide for itself where a customer's data lands.\n\n`enrich_after_export` and its enrichment configs are deliberately not\naccepted here: they spend credits, and a spend should not be a side effect\nof an export call.","operationId":"export_workbench_table_workbench_tables__table_id__export_post","parameters":[{"name":"table_id","in":"path","required":true,"schema":{"type":"string","description":"Table id (UUID).","title":"Table Id"},"description":"Table id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkbenchExportRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"lists:write","x-graph8-lifecycle":"active"}},"/search/filter-options":{"get":{"tags":["Search"],"summary":"Get Filter Options","description":"Every distinct value a field holds, across the whole open-data index.\n\nRead this BEFORE writing a filter. The `id` of each option is exactly what\n`POST /search/{resource}` expects as a filter value, so the two can be\nchained without any guessing in between.\n\nCached server-side, so repeated calls are cheap. It does not consume\ncredits.","operationId":"get_filter_options_search_filter_options_get","parameters":[{"name":"resource","in":"query","required":true,"schema":{"enum":["contacts","companies"],"type":"string","description":"Which vocabulary the field names are in.","title":"Resource"},"description":"Which vocabulary the field names are in."},{"name":"fields","in":"query","required":true,"schema":{"type":"array","items":{"type":"string"},"description":"Developer field names, REPEATABLE (`?fields=company_industry&fields=seniority_level`). The same names `POST /search/{resource}` takes.","title":"Fields"},"description":"Developer field names, REPEATABLE (`?fields=company_industry&fields=seniority_level`). The same names `POST /search/{resource}` takes."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__list_FilterOptionItem___"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"search:read","x-graph8-lifecycle":"active"},"post":{"tags":["Search"],"summary":"Get Filtered Filter Options","description":"The same values, but only those present in a SUBSET of the index.\n\nThe difference matters: `GET /search/filter-options` answers \"what\nindustries exist\", this answers \"what industries exist among companies in\nSpain\". Building a dependent filter off the unfiltered list offers the\ncaller values that cannot return a single row once the other filters are\napplied.\n\n`filters` must contain at least one condition, which is the same refusal\n`POST /search/contacts` makes - an unfiltered request scans the entire\nopen-data index.","operationId":"get_filtered_filter_options_search_filter_options_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FilterOptionsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__list_FilterOptionItem___"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"search:read","x-graph8-lifecycle":"active"}},"/search/filter-options/intent-topics":{"get":{"tags":["Search"],"summary":"List Intent Topics","description":"The intent topics a buying-intent filter can name.\n\nTopics carry their own numeric ids rather than the string ids the other\nfilter options use, so this is a separate read rather than another entry\nin `filter-options`.","operationId":"list_intent_topics_search_filter_options_intent_topics_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"search:read","x-graph8-lifecycle":"active"}},"/search/autocomplete":{"get":{"tags":["Search"],"summary":"Get Autocomplete Suggestions","description":"Type-ahead over one field's values.\n\nThe counterpart to `filter-options` for fields whose value set is too large\nto enumerate - company name and domain especially, where the backend also\nexpands domains (`amazon` matches `amazon.com`) and ranks by company score\nrather than alphabetically.","operationId":"get_autocomplete_suggestions_search_autocomplete_get","parameters":[{"name":"resource","in":"query","required":true,"schema":{"enum":["contacts","companies"],"type":"string","description":"Which vocabulary `field` is in.","title":"Resource"},"description":"Which vocabulary `field` is in."},{"name":"field","in":"query","required":true,"schema":{"type":"string","description":"Developer field name to search within.","title":"Field"},"description":"Developer field name to search within."},{"name":"value","in":"query","required":true,"schema":{"type":"string","description":"What the person has typed so far.","title":"Value"},"description":"What the person has typed so far."},{"name":"size","in":"query","required":false,"schema":{"type":"integer","maximum":20,"minimum":1,"description":"How many suggestions to return.","default":5,"title":"Size"},"description":"How many suggestions to return."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SearchDiscoveryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"search:read","x-graph8-lifecycle":"active"}},"/search/saved-searches":{"get":{"tags":["Search"],"summary":"List Saved Searches","description":"Saved searches belonging to the KEY'S OWN identity.\n\nScoped server-side to one identity rather than to the organisation, exactly\nas the in-app route is - so this lists what the key itself saved, not what\nthe whole team saved. A personal key sees the minting user's saved\nsearches; an organisation key has no person behind it and sees only what\nthat credential saved through this API.","operationId":"list_saved_searches_search_saved_searches_get","parameters":[{"name":"scope","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only saved searches over this resource, e.g. `contacts`.","title":"Scope"},"description":"Only saved searches over this resource, e.g. `contacts`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"search:read","x-graph8-lifecycle":"active"},"post":{"tags":["Search"],"summary":"Save Search","description":"Store a search so it can be run again.\n\nSending `id` REPLACES that saved search rather than creating a second one -\nwhich is why a caller looping over a list should send the id back, not omit\nit. A saved search belonging to someone else comes back as a 404 rather\nthan a 403, so a guessed id cannot confirm that it exists.\n\n`icp_query` is stored verbatim and is not interpreted here.","operationId":"save_search_search_saved_searches_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SaveSearchRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SearchDiscoveryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"search:write","x-graph8-lifecycle":"active"}},"/search/saved-searches/{query_id}":{"delete":{"tags":["Search"],"summary":"Delete Saved Search","description":"Delete a saved search.\n\nSOFT: the row is marked deleted rather than removed, and nothing that was\never found by it is touched. Someone else's saved search is a 404, not a\n403, for the same reason the write above is.","operationId":"delete_saved_search_search_saved_searches__query_id__delete","parameters":[{"name":"query_id","in":"path","required":true,"schema":{"type":"integer","description":"Saved-search id.","title":"Query Id"},"description":"Saved-search id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SearchDiscoveryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"search:delete","x-graph8-lifecycle":"active"}},"/search/contacts":{"post":{"tags":["Search"],"summary":"Search Contacts","description":"Search open contact data with the org's deliverability policy applied.","operationId":"search_contacts_search_contacts_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_SearchContactItem__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"search:run","x-graph8-lifecycle":"active"}},"/search/companies":{"post":{"tags":["Search"],"summary":"Search Companies","description":"Search open company data with the org's deliverability policy applied.","operationId":"search_companies_search_companies_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_SearchCompanyItem__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"search:run","x-graph8-lifecycle":"active"}},"/search/contacts/save":{"post":{"tags":["Search"],"summary":"Save Contact Search","description":"Search protected contact data and save matching results to a new list.","operationId":"save_contact_search_search_contacts_save_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SearchSaveRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SearchSaveResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"search:run","x-graph8-lifecycle":"active"}},"/search/companies/save":{"post":{"tags":["Search"],"summary":"Save Company Search","description":"Search companies and save matching results to a new list.","operationId":"save_company_search_search_companies_save_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SearchSaveRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SearchSaveResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"search:run","x-graph8-lifecycle":"active"}},"/search/contacts/count-variants":{"post":{"tags":["Search"],"summary":"Count Contact Search Variants","description":"How many contacts each filter set matches: the zero-results \"without this filter\" counts. No rows, no credits.","operationId":"count_contact_search_variants_search_contacts_count_variants_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SearchCountVariantsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SearchCountVariantsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"search:read","x-graph8-lifecycle":"active"}},"/search/companies/count-variants":{"post":{"tags":["Search"],"summary":"Count Company Search Variants","description":"How many companies each filter set matches: the zero-results \"without this filter\" counts. No rows, no credits.","operationId":"count_company_search_variants_search_companies_count_variants_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SearchCountVariantsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SearchCountVariantsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"search:read","x-graph8-lifecycle":"active"}},"/sequencer/channels/mailboxes":{"get":{"tags":["Sequences"],"summary":"List Sequencer Mailboxes","description":"Mailboxes available to send from, annotated as the app annotates them.\n\nCarries the same warming, daily-capacity, warmup-ready and SURBL-listed\nannotations the in-app picker shows, so a rebuilt builder can surface the\nsame warnings rather than silently offering a mailbox that cannot send.","operationId":"list_sequencer_mailboxes_sequencer_channels_mailboxes_get","parameters":[{"name":"email","in":"query","required":true,"schema":{"type":"string","description":"Mailbox email to scope the picker to.","title":"Email"},"description":"Mailbox email to scope the picker to."},{"name":"exclude_sequence_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Hide mailboxes already attached to this sequence.","title":"Exclude Sequence Id"},"description":"Hide mailboxes already attached to this sequence."},{"name":"include_nurture","in":"query","required":false,"schema":{"type":"boolean","description":"Include nurture-only mailboxes.","default":false,"title":"Include Nurture"},"description":"Include nurture-only mailboxes."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Any_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/channels/phone_numbers":{"get":{"tags":["Sequences"],"summary":"List Sequencer Phone Numbers","description":"Voice-capable numbers available to a sequence.\n\nNOTE these are the VOICE service's numbers, not the CDP `phone_numbers`\ntable behind Settings -> Phone Numbers. Different tables, same word.","operationId":"list_sequencer_phone_numbers_sequencer_channels_phone_numbers_get","parameters":[{"name":"exclude_sequence_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Exclude Sequence Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Any_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/channels/sms_numbers":{"get":{"tags":["Sequences"],"summary":"List Sequencer Sms Numbers","description":"SMS-capable numbers, annotated with SMS readiness.","operationId":"list_sequencer_sms_numbers_sequencer_channels_sms_numbers_get","parameters":[{"name":"exclude_sequence_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Exclude Sequence Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Any_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/channels/whatsapp_numbers":{"get":{"tags":["Sequences"],"summary":"List Sequencer Whatsapp Numbers","description":"WhatsApp-enabled numbers.","operationId":"list_sequencer_whatsapp_numbers_sequencer_channels_whatsapp_numbers_get","parameters":[{"name":"exclude_sequence_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Exclude Sequence Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Any_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/channels/whatsapp_templates":{"get":{"tags":["Sequences"],"summary":"List Sequencer Whatsapp Templates","description":"Approved WhatsApp message templates.\n\nA WhatsApp step cannot be composed freely - it must reference an approved\ntemplate, so this is required, not decorative.","operationId":"list_sequencer_whatsapp_templates_sequencer_channels_whatsapp_templates_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Any_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/channels/capacity-estimate":{"get":{"tags":["Sequences"],"summary":"Get Sequencer Capacity Estimate","description":"How many mailboxes and domains a target volume needs, and what it costs.\n\nRead-only: it computes an estimate and buys nothing.","operationId":"get_sequencer_capacity_estimate_sequencer_channels_capacity_estimate_get","parameters":[{"name":"contacts_per_month","in":"query","required":true,"schema":{"type":"integer","minimum":0,"description":"Target contacts to reach per month.","title":"Contacts Per Month"},"description":"Target contacts to reach per month."},{"name":"warmed","in":"query","required":false,"schema":{"type":"boolean","description":"False = cold start (25/day); True = warmed (100/day).","default":false,"title":"Warmed"},"description":"False = cold start (25/day); True = warmed (100/day)."},{"name":"domain_tld","in":"query","required":false,"schema":{"type":"string","description":"TLD for the per-domain USD cost estimate.","default":".com","title":"Domain Tld"},"description":"TLD for the per-domain USD cost estimate."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Any_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/agents/textual":{"get":{"tags":["Sequences"],"summary":"List Sequencer Textual Agents","description":"Textual agents that can run an email or LinkedIn step.","operationId":"list_sequencer_textual_agents_sequencer_agents_textual_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Any_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/agents/voice":{"get":{"tags":["Sequences"],"summary":"List Sequencer Voice Agents","description":"Voice agents that can run a call step.\n\nRaises the app's own error when the org has no voice subscription, rather\nthan returning an empty list that would read as \"no agents configured\".","operationId":"list_sequencer_voice_agents_sequencer_agents_voice_get","parameters":[{"name":"agent_name","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by agent name.","title":"Agent Name"},"description":"Filter by agent name."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Any_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/stats":{"get":{"tags":["Sequences"],"summary":"Get Sequence Stats","description":"Per-step delivery and engagement counts.\n\n`skip_reason_breakdown` is SEQUENCE-level and counted once per contact, so\nits total can be LESS than the per-step `skipped` tiles sum to - the\ndurable-LinkedIn-skip cascade writes one receipt per contiguous LinkedIn\nstep, and a skip with no recorded reason is omitted. The two are not meant\nto reconcile.","operationId":"get_sequence_stats_sequences__sequence_id__stats_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceStats_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/routing-summary":{"get":{"tags":["Sequences"],"summary":"Get Sequence Routing Summary","description":"Which providers this sequence's recipients sit behind, and what is suppressed.\n\nTwo properties that change how the answer should be read:\n\n  * APPROXIMATE - it scans up to 10,000 recipients, not all of them.\n  * FAIL-OPEN - on any error every count is zero, so an all-zero summary\n    means \"could not compute\" just as much as \"nothing matched\". Do not\n    render it as a confident zero.\n\nEach recipient lands in exactly ONE bucket, suppression beating routing\n(bounce > seg > personal), so the buckets partition the scanned set rather\nthan overlapping.","operationId":"get_sequence_routing_summary_sequences__sequence_id__routing_summary_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceRoutingSummary_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/terminate":{"post":{"tags":["Sequences"],"summary":"Terminate Sequence","description":"End a sequence for good. Enrolled contacts stop; this is not a pause.\n\nThe path drops the app's `-v2` suffix: v1 is gone, so there is nothing\nleft to disambiguate from on a public surface.","operationId":"terminate_sequence_sequences__sequence_id__terminate_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/archive":{"post":{"tags":["Sequences"],"summary":"Archive Sequence","description":"Archive a sequence - a soft delete.\n\nNOT REVERSIBLE THROUGH THIS API TODAY. The app's `unarchive` endpoint is a\nreserved stub that unconditionally returns 403 (\"Unarchiving is not\navailable yet\"), so it is not published here - archiving is a one-way door\nfor an API caller until that lands. Contact support to restore one.\n\nA LIVE or WAITING sequence is paused first and wound down in the\nbackground; `is_archived` blocks every worker immediately. Archiving one\nthat is already archived is a 400, and one mid-transition (scheduling,\npausing) is a 409, so a retry loop cannot corrupt the state machine.","operationId":"archive_sequence_sequences__sequence_id__archive_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"sequences:delete","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/sync":{"post":{"tags":["Sequences"],"summary":"Sync Sequence","description":"Re-pull the associated list so newly-matching contacts enrol.\n\nThis is how a live sequence picks up people added to its list after it\nstarted. It enrols real recipients, so it is a write, not a refresh.","operationId":"sync_sequence_sequences__sequence_id__sync_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/status":{"post":{"tags":["Sequences"],"summary":"Set Sequence Status","description":"Drive the status machine directly. PREFER THE NAMED TRANSITIONS.\n\n`/launch`, `/pause`, `/resume`, `/terminate` and `/archive` each run the\nwind-down, scheduling and event work that belongs to them. This endpoint\nonly SETS THE STATUS, so a sequence moved to `terminated` this way never\nemits its termination event and its workers are never wound down. It is\nexposed because the app exposes it and a rebuilt settings panel uses it -\nnot because it is the way to stop a sequence.\n\nThe app's state machine rejects an illegal transition.","operationId":"set_sequence_status_sequences__sequence_id__status_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SequenceStatusRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceRecord_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/duplicate":{"post":{"tags":["Sequences"],"summary":"Duplicate Sequence","description":"Copy a sequence. The copy is drafted, owned by the caller, no channels.\n\n`user_email` is pinned to the caller by the app even if one is sent, which\nis why the request model does not offer it.","operationId":"duplicate_sequence_sequences__sequence_id__duplicate_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id to copy.","title":"Sequence Id"},"description":"Sequence id to copy."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SequenceDuplicateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceRecord_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/campaign":{"put":{"tags":["Sequences"],"summary":"Link Sequence Campaign","description":"Attach this sequence to a Studio campaign.\n\n`campaign_id` is declared REQUIRED here. The app takes a bare `dict` and\n400s on a missing key - a typed model turns that into a 422 with the field\nnamed, which is what a contract is for.","operationId":"link_sequence_campaign_sequences__sequence_id__campaign_put","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SequenceCampaignLinkRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceRecord_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Sequences"],"summary":"Unlink Sequence Campaign","description":"Detach the Studio campaign. The sequence and the campaign both survive.","operationId":"unlink_sequence_campaign_sequences__sequence_id__campaign_delete","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceRecord_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"sequences:delete","x-graph8-lifecycle":"active"}},"/sequences":{"get":{"tags":["Sequences"],"summary":"List Sequences","description":"List all sequences with optional status / sequence_kind filters.","operationId":"list_sequences_sequences_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number","default":1,"title":"Page"},"description":"Page number"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page","default":50,"title":"Limit"},"description":"Items per page"},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by status","title":"Status"},"description":"Filter by status"},{"name":"sequence_kind","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by sequence kind ('cold_outbound' or 'nurture'). Omit to list all kinds.","title":"Sequence Kind"},"description":"Filter by sequence kind ('cold_outbound' or 'nurture'). Omit to list all kinds."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_SequenceListItem__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"},"post":{"tags":["Sequence Lifecycle"],"summary":"Create Sequence","description":"Create a new sequence with optional steps and channels.","operationId":"create_sequence_sequences_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SequenceCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceCreateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}":{"get":{"tags":["Sequences"],"summary":"Get Sequence","description":"Get detailed information about a sequence.","operationId":"get_sequence_sequences__sequence_id__get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence ID","title":"Sequence Id"},"description":"Sequence ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceDetailResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Sequence Lifecycle"],"summary":"Update Sequence","description":"Update sequence metadata. Rejects PATCH when status is transitional (409).","operationId":"update_sequence_sequences__sequence_id__patch","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence ID","title":"Sequence Id"},"description":"Sequence ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SequenceUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceActionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Sequence Lifecycle"],"summary":"Delete Sequence","description":"Soft-delete (archive) a sequence. Sets is_archived=True.","operationId":"delete_sequence_sequences__sequence_id__delete","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence ID","title":"Sequence Id"},"description":"Sequence ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceActionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"sequences:delete","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/run":{"post":{"tags":["Sequences"],"summary":"Run Sequence","description":"Run/start a drafted sequence using V2 orchestration.","operationId":"run_sequence_sequences__sequence_id__run_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence ID","title":"Sequence Id"},"description":"Sequence ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceActionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/pause":{"post":{"tags":["Sequences"],"summary":"Pause Sequence","description":"Pause a live sequence.","operationId":"pause_sequence_sequences__sequence_id__pause_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence ID","title":"Sequence Id"},"description":"Sequence ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceActionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/resume":{"post":{"tags":["Sequences"],"summary":"Resume Sequence","description":"Resume a paused sequence.","operationId":"resume_sequence_sequences__sequence_id__resume_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence ID","title":"Sequence Id"},"description":"Sequence ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceActionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/contacts":{"get":{"tags":["Sequences"],"summary":"List Sequence Contacts","description":"List contacts in a sequence with pagination.","operationId":"list_sequence_contacts_sequences__sequence_id__contacts_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence ID","title":"Sequence Id"},"description":"Sequence ID"},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number","default":1,"title":"Page"},"description":"Page number"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page","default":50,"title":"Limit"},"description":"Items per page"},{"name":"state","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by contact state","title":"State"},"description":"Filter by contact state"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_SequenceContactItem__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"},"post":{"tags":["Sequences"],"summary":"Add Contacts To Sequence","description":"Add contacts to a live or drafted sequence using V2 queuing.","operationId":"add_contacts_to_sequence_sequences__sequence_id__contacts_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence ID","title":"Sequence Id"},"description":"Sequence ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AddSequenceContactsRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceActionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/sequences/generate-spintax":{"post":{"tags":["Sequences"],"summary":"Generate Sequence Spintax","description":"One-time AI generation: rewrite a manual email into spintax.\n\nReturns the subject + body rewritten with (possibly nested)\n``{{option a|option b}}`` blocks; the sequencer's per-contact resolver\nthen sends a different-looking variant to each lead. Content-level and\nsequence-agnostic: paste the result into any sequence or campaign email\nstep as a MANUAL_TEMPLATE.\n\nRequires an active subscription and consumes credits (token-metered;\n402 on either failure). Synchronous, up to ~2 minutes; per-worker\nconcurrency is capped (429 + Retry-After when saturated). Output is\nvalidated server-side (balanced braces, ``{{variables}}`` and links\npreserved) - invalid model output surfaces as 422, never as silently\nbroken content.","operationId":"generate_sequence_spintax_sequences_generate_spintax_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/GenerateSpintaxRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GenerateSpintaxResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/nurtures":{"get":{"tags":["Sequences"],"summary":"List Nurtures","description":"Nurtures visible to this key - its own plus org-shared.\n\nNo per-record gate here: a LIST is filtered by `sequence_scope` rather than\nchecked row by row, which is the same shape the app uses.","operationId":"list_nurtures_nurtures_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (1-indexed).","default":1,"title":"Page"},"description":"Page number (1-indexed)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page (max 200).","default":50,"title":"Limit"},"description":"Items per page (max 200)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NurtureListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"},"post":{"tags":["Sequences"],"summary":"Create Nurture","description":"Create a nurture.\n\n`sequence_kind` is pinned to `nurture` by the app and re-validated there,\nso the nurture-specific channel rules fire even though this endpoint never\naccepts the field. `user_email` defaults to the identity the key was\nminted under; a personal nurture owned by anyone else is a 403.","operationId":"create_nurture_nurtures_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NurtureCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NurtureResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/nurtures/{nurture_id}":{"get":{"tags":["Sequences"],"summary":"Get Nurture","description":"Read one nurture. 404s if it is not a nurture, or not yours to see.","operationId":"get_nurture_nurtures__nurture_id__get","parameters":[{"name":"nurture_id","in":"path","required":true,"schema":{"type":"string","description":"Nurture id.","title":"Nurture Id"},"description":"Nurture id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NurtureResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Sequences"],"summary":"Update Nurture","description":"Patch a nurture. Omitted fields are left alone.\n\n`exclude_unset` rather than `exclude_none`: the app distinguishes \"field\nabsent\" from \"field explicitly set to null\", and collapsing the two would\nmake it impossible to clear an optional field such as `schedule_id`.","operationId":"update_nurture_nurtures__nurture_id__patch","parameters":[{"name":"nurture_id","in":"path","required":true,"schema":{"type":"string","description":"Nurture id.","title":"Nurture Id"},"description":"Nurture id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NurtureUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NurtureResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Sequences"],"summary":"Delete Nurture","description":"Archive a nurture - a soft delete, not a purge.\n\nA LIVE or WAITING nurture is paused first and wound down in the\nbackground; `is_archived` blocks every worker immediately. Archiving an\nalready-archived nurture is a 400, and one mid-transition (scheduling,\npausing) is a 409, so a retry loop cannot corrupt the state machine.","operationId":"delete_nurture_nurtures__nurture_id__delete","parameters":[{"name":"nurture_id","in":"path","required":true,"schema":{"type":"string","description":"Nurture id.","title":"Nurture Id"},"description":"Nurture id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"sequences:delete","x-graph8-lifecycle":"active"}},"/nurtures/{nurture_id}/pause":{"post":{"tags":["Sequences"],"summary":"Pause Nurture","description":"Pause a running nurture. Stops further sends; does not terminate it.","operationId":"pause_nurture_nurtures__nurture_id__pause_post","parameters":[{"name":"nurture_id","in":"path","required":true,"schema":{"type":"string","description":"Nurture id.","title":"Nurture Id"},"description":"Nurture id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/nurtures/{nurture_id}/resume":{"post":{"tags":["Sequences"],"summary":"Resume Nurture","description":"Resume a paused nurture.","operationId":"resume_nurture_nurtures__nurture_id__resume_post","parameters":[{"name":"nurture_id","in":"path","required":true,"schema":{"type":"string","description":"Nurture id.","title":"Nurture Id"},"description":"Nurture id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/nurtures/{nurture_id}/launch":{"post":{"tags":["Sequences"],"summary":"Launch Nurture","description":"Launch a nurture. THIS SENDS REAL MESSAGES TO REAL PEOPLE.\n\nProxies the same v2 run flow the app's Go-Live button uses, so enrollment,\nschedule and consent checks are identical.\n\nWHY THE PATH IS `/launch` AND NOT THE APP'S `/run/v2`\n-----------------------------------------------------\nTwo reasons, and the second is the load-bearing one.\n\nThe `v2` suffix is noise: v1 was removed on 2026-04-21, so there is nothing\nleft to disambiguate from on a public surface.\n\n`launch` rather than `run` is what gets this operation the right SCOPE.\n`build_scope_policy.EXTERNAL_PATH_MARKERS` contains `/launch`, `/send` and\n`/publish` - the fragments that mean \"this reaches the outside world\" - and\nan external-tier operation resolves to the `run` ACTION, so the key needs\nan explicit `sequences:run` grant rather than plain `sequences:write`. As\n`/run` this endpoint classified as an ordinary write, one tier below the\nidentical `POST /sequences/{id}/run`, which is external. Sending real email\nto real people is the definition of external, and the customer issuing a\nkey should be able to grant \"edit my nurtures\" without granting \"start\nsending\".","operationId":"launch_nurture_nurtures__nurture_id__launch_post","parameters":[{"name":"nurture_id","in":"path","required":true,"schema":{"type":"string","description":"Nurture id.","title":"Nurture Id"},"description":"Nurture id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/nurtures/{nurture_id}/duplicate":{"post":{"tags":["Sequences"],"summary":"Duplicate Nurture","description":"Copy a nurture. The copy is drafted, owned by the caller, no channels.\n\n`user_email` is pinned to the caller by the app even if one is sent, which\nis why the request model does not offer it.","operationId":"duplicate_nurture_nurtures__nurture_id__duplicate_post","parameters":[{"name":"nurture_id","in":"path","required":true,"schema":{"type":"string","description":"Nurture id to copy.","title":"Nurture Id"},"description":"Nurture id to copy."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NurtureDuplicateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NurtureResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/preview":{"get":{"tags":["Sequence Lifecycle"],"summary":"Preview Sequence","description":"Load a sequence with its steps and channels, including RESOLVED copy. No enrollment.\n\nEach step carries both:\n\n- ``step_data``: the stored template, exactly as written, spintax braces and all.\n- ``rendered``: the same copy with spintax collapsed to one real variant, plus\n  ``total_combinations`` and up to three sample ``variants``.\n\nUse ``rendered`` to answer \"is my spintax working?\". If ``variants`` differ from\neach other, per-contact variation is live and each lead gets a different email.\n``{{variables}}`` stay visible in ``rendered`` on purpose; they fill in at send\ntime from contact data, and a preview has no contact to fill them from.\n\n``rendered`` is null for ON_DEMAND steps, whose copy the AI writes per contact\nat send time rather than reading from ``step_data``.","operationId":"preview_sequence_sequences__sequence_id__preview_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence ID","title":"Sequence Id"},"description":"Sequence ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencePreviewResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/steps":{"get":{"tags":["Sequence Lifecycle"],"summary":"List Sequence Steps","description":"List a sequence's steps with their resolved copy. Read-only, no enrollment.\n\nThe step list from ``/preview`` without the sequence and channel envelope. Each\nstep carries the same ``rendered`` block described on ``/preview``, so this is\nthe direct way to check what a given step will actually send.","operationId":"list_sequence_steps_sequences__sequence_id__steps_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence ID","title":"Sequence Id"},"description":"Sequence ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceStepsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"},"post":{"tags":["Sequences"],"summary":"Add Sequence Steps","description":"Add one or more steps to an existing sequence. Answers with EVERY step now in it.\n\nThe content is validated on write, as in the app: copy that cannot render\n(broken spintax, unclosed merge tags) is a 400 naming the problem, and\nhand-written copy on an `ON_DEMAND` step - which the generator would\nsilently discard - is refused rather than accepted and dropped.","operationId":"add_sequence_steps_sequences__sequence_id__steps_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AddStepsRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/steps/{step_id}":{"patch":{"tags":["Sequence Lifecycle"],"summary":"Update Sequence Step","description":"Update a single step within a sequence.","operationId":"update_sequence_step_sequences__sequence_id__steps__step_id__patch","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence ID","title":"Sequence Id"},"description":"Sequence ID"},{"name":"step_id","in":"path","required":true,"schema":{"type":"string","description":"Step ID","title":"Step Id"},"description":"Step ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StepUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceActionResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Sequences"],"summary":"Delete Sequence Step","description":"Permanently delete a step. Returns the sequence's remaining steps.","operationId":"delete_sequence_step_sequences__sequence_id__steps__step_id__delete","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"step_id","in":"path","required":true,"schema":{"type":"string","description":"Step id.","title":"Step Id"},"description":"Step id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceOpsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"sequences:delete","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/analytics":{"get":{"tags":["Sequence Lifecycle"],"summary":"Get Sequence Analytics","description":"Get comprehensive analytics for a sequence.","operationId":"get_sequence_analytics_sequences__sequence_id__analytics_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence ID","title":"Sequence Id"},"description":"Sequence ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceAnalyticsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/channels/linkedin":{"delete":{"tags":["Sequence Lifecycle"],"summary":"Remove Linkedin Channel","description":"Remove this sequence's LinkedIn steps AND its LinkedIn channel, atomically.\n\nUnbinding the channel on its own leaves the LinkedIn steps with no sender,\nwhich makes the sequence impossible to run or resume (400, and the sequence is\nreverted to DRAFTED) and pauses it outright if a contact reaches the step. This\nendpoint removes both halves in one transaction so that state is never created.\n\nA sequence with no LinkedIn binding returns 200 with zero counts rather than\n404, so it is safe to call across a batch. It also cleans up sequences already\nstranded with orphaned LinkedIn steps.","operationId":"remove_linkedin_channel_sequences__sequence_id__channels_linkedin_delete","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence ID","title":"Sequence Id"},"description":"Sequence ID"},{"name":"dry_run","in":"query","required":false,"schema":{"type":"boolean","description":"Preview exactly what would be removed without writing anything.","default":false,"title":"Dry Run"},"description":"Preview exactly what would be removed without writing anything."},{"name":"force","in":"query","required":false,"schema":{"type":"boolean","description":"Required to operate on a LIVE or WAITING sequence. The sequence is paused afterwards either way so the result can be reviewed before it resumes sending.","default":false,"title":"Force"},"description":"Required to operate on a LIVE or WAITING sequence. The sequence is paused afterwards either way so the result can be reviewed before it resumes sending."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LinkedInChannelRemovalResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"sequences:delete","x-graph8-lifecycle":"active"}},"/sequencer/templates/sequences":{"get":{"tags":["Sequences"],"summary":"List Sequence Templates","description":"The organisation's sequence templates, INCLUDING archived ones.\n\nEach row carries `is_archived`; filter on it client-side. Org-SHARED:\nevery key in the organisation sees the same list.","operationId":"list_sequence_templates_sequencer_templates_sequences_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"},"post":{"tags":["Sequences"],"summary":"Create Sequence Template","description":"Save a reusable sequence skeleton.\n\nAnswers with the FULL template list, not the new row - that is the app's\nresponse, kept so the two cannot disagree about what was created.","operationId":"create_sequence_template_sequencer_templates_sequences_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateSequenceTemplateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/sequencer/templates/sequences/{sequence_template_id}":{"patch":{"tags":["Sequences"],"summary":"Update Sequence Template","description":"Change a sequence template. Only what you send is written; an unknown id is a 404.","operationId":"update_sequence_template_sequencer_templates_sequences__sequence_template_id__patch","parameters":[{"name":"sequence_template_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence template id.","title":"Sequence Template Id"},"description":"Sequence template id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateSequenceTemplateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/sequencer/templates/sequences/{sequence_template_id}/archive":{"patch":{"tags":["Sequences"],"summary":"Archive Sequence Template","description":"Archive or UN-archive a sequence template (`is_archived` is explicit).\n\nNothing is deleted - the row stays in the list with `is_archived` set.","operationId":"archive_sequence_template_sequencer_templates_sequences__sequence_template_id__archive_patch","parameters":[{"name":"sequence_template_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence template id.","title":"Sequence Template Id"},"description":"Sequence template id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ArchiveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"sequences:delete","x-graph8-lifecycle":"active"}},"/sequencer/templates/steps":{"get":{"tags":["Sequences"],"summary":"List Step Templates","description":"The organisation's reusable step content, archived rows included. Org-SHARED.","operationId":"list_step_templates_sequencer_templates_steps_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"},"post":{"tags":["Sequences"],"summary":"Create Step Template","description":"Save reusable step content. Answers with the full list, as the app does.","operationId":"create_step_template_sequencer_templates_steps_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateStepTemplateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/sequencer/templates/steps/generate":{"post":{"tags":["Sequences"],"summary":"Generate Step Templates","description":"Have an agent DRAFT step content. Spends credits on every call.\n\nNothing is saved - the drafts come back for you to keep with\n`POST /sequencer/templates/steps` or discard. It runs a full model\ngeneration and can take tens of seconds; a 402 means the organisation is\nout of credits.","operationId":"generate_step_templates_sequencer_templates_steps_generate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/GenerateStepTemplatesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/sequencer/templates/steps/{step_template_id}":{"patch":{"tags":["Sequences"],"summary":"Update Step Template","description":"Change a step template. An unknown id is a 404.","operationId":"update_step_template_sequencer_templates_steps__step_template_id__patch","parameters":[{"name":"step_template_id","in":"path","required":true,"schema":{"type":"string","description":"Step template id.","title":"Step Template Id"},"description":"Step template id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateStepTemplateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/sequencer/templates/steps/{step_template_id}/archive":{"patch":{"tags":["Sequences"],"summary":"Archive Step Template","description":"Archive or un-archive a step template (`is_archived` is explicit).","operationId":"archive_step_template_sequencer_templates_steps__step_template_id__archive_patch","parameters":[{"name":"step_template_id","in":"path","required":true,"schema":{"type":"string","description":"Step template id.","title":"Step Template Id"},"description":"Step template id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ArchiveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"sequences:delete","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/channels":{"get":{"tags":["Sequences"],"summary":"List Sequence Channels","description":"The mailboxes, numbers and accounts this sequence sends from.\n\nEach row's `id` is the SEQUENCE-CHANNEL id - what the detach routes take -\nnot the mailbox or number id itself (that is `channel_id`).","operationId":"list_sequence_channels_sequences__sequence_id__channels_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"},"post":{"tags":["Sequences"],"summary":"Add Sequence Channels","description":"Attach senders to a sequence. Answers with every channel now attached.\n\nTake the values from the `/sequencer/channels/*` pickers: `channel_id` is\nthe sender's own id and `channel_value` its address.","operationId":"add_sequence_channels_sequences__sequence_id__channels_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AddChannelsRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Sequences"],"summary":"Remove Sequence Channels","description":"Detach several senders at once. Answers with the channels that remain.\n\nA 409 means the detach would leave LinkedIn steps with no LinkedIn sender,\nwhich would stop the sequence on its next run - detach the steps first.","operationId":"remove_sequence_channels_sequences__sequence_id__channels_delete","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RemoveChannelsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"sequences:delete","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/channels/{sequence_channel_id}":{"delete":{"tags":["Sequences"],"summary":"Remove Sequence Channel","description":"Detach one sender. Answers with the channels that remain.\n\nScoped to THIS sequence: a channel id belonging to another sequence\ndetaches nothing. Same 409 as the bulk form.","operationId":"remove_sequence_channel_sequences__sequence_id__channels__sequence_channel_id__delete","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"sequence_channel_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence-channel id, from `GET .../channels`.","title":"Sequence Channel Id"},"description":"Sequence-channel id, from `GET .../channels`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"sequences:delete","x-graph8-lifecycle":"active"}},"/sequencer/dialer/sequences":{"get":{"tags":["Sequences"],"summary":"List Dialer Sequences","description":"Sequences the dialer can work, each with its steps, paged.\n\nFiltered by the key's sequence scope exactly as the in-app dropdown is, so\na key limited to its own sequences sees only those.","operationId":"list_dialer_sequences_sequencer_dialer_sequences_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":20,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"sort_by","in":"query","required":false,"schema":{"enum":["created_at","updated_at","name","status"],"type":"string","default":"created_at","title":"Sort By"}},{"name":"sort_order","in":"query","required":false,"schema":{"enum":["asc","desc"],"type":"string","default":"desc","title":"Sort Order"}},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Sequence name contains.","title":"Search"},"description":"Sequence name contains."},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only sequences in this status, e.g. `running`.","title":"Status"},"description":"Only sequences in this status, e.g. `running`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/dialer/sequences/{sequence_id}/contacts":{"get":{"tags":["Sequences"],"summary":"List Dialer Contacts","description":"The contacts of one dialer sequence with their step progress, paged.\n\nCarries the sequence's `associated_list_id`, so a caller can go from \"who\nis due a call\" to the list they came from without a second lookup.","operationId":"list_dialer_contacts_sequencer_dialer_sequences__sequence_id__contacts_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":20,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"sort_by","in":"query","required":false,"schema":{"enum":["created_at","current_step_order","state","current_step_execution_at"],"type":"string","default":"created_at","title":"Sort By"}},{"name":"sort_order","in":"query","required":false,"schema":{"enum":["asc","desc"],"type":"string","default":"desc","title":"Sort Order"}},{"name":"state","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only contacts in this state.","title":"State"},"description":"Only contacts in this state."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/dialer/sequences/{sequence_id}/contacts/{contact_id}/callback":{"post":{"tags":["Sequences"],"summary":"Record Dialer Outcome","description":"Record that an SDR finished a dialer call, advancing the contact.\n\nA 400 means the contact is not in this sequence or is not waiting on a\ndialer step; the message says which.","operationId":"record_dialer_outcome_sequencer_dialer_sequences__sequence_id__contacts__contact_id__callback_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"The contact's integer id in this sequence.","title":"Contact Id"},"description":"The contact's integer id in this sequence."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DialerCallbackRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/sequencer/content/email/models":{"get":{"tags":["Sequences"],"summary":"List Email Draft Models","description":"The models an email draft can use, and which one is the default.\n\nPass a row's `provider` and `model` to the draft and estimate routes. Never\nfails: if the catalog cannot be fetched the built-in default list is\nreturned.","operationId":"list_email_draft_models_sequencer_content_email_models_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/content/email/estimate":{"post":{"tags":["Sequences"],"summary":"Estimate Email Draft","description":"What drafting this email WOULD cost, in credits - without drafting it. Free.\n\nTakes exactly the body of `.../email/generate`, and builds the identical\nprompt, so the number is what that call is billed. `cached: true` with\n`estimated_credits: 0` means the draft would be served from cache free.\nA 503 means the price list is unavailable - the cost is unknown, not zero.","operationId":"estimate_email_draft_sequencer_content_email_estimate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DraftEmailRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/content/email/generate":{"post":{"tags":["Sequences"],"summary":"Draft Email","description":"Draft one contact's email with an agent. SPENDS CREDITS per call.\n\nReturns the subject and body; nothing is saved or sent. A 402 means the\norganisation is out of credits. Price it first with `.../email/estimate`.","operationId":"draft_email_sequencer_content_email_generate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DraftEmailRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/sequencer/content/linkedin/generate":{"post":{"tags":["Sequences"],"summary":"Draft Linkedin Message","description":"Draft one contact's LinkedIn message with an agent. SPENDS CREDITS per call.\n\nReturns `message` (and `subject` for an InMail); nothing is saved or sent.","operationId":"draft_linkedin_message_sequencer_content_linkedin_generate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DraftLinkedInRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/sequencer/channels/linkedin_accounts":{"get":{"tags":["Sequences"],"summary":"List Linkedin Accounts","description":"LinkedIn accounts a sequence can send from, bucketed by allocation status.\n\nThe last missing member of the published picker family. The path keeps\nthe family's underscore spelling (`/sequencer/channels/phone_numbers` and\nits siblings already ship).","operationId":"list_linkedin_accounts_sequencer_channels_linkedin_accounts_get","parameters":[{"name":"exclude_sequence_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Treat accounts already allocated to THIS sequence as available. Pass the sequence being edited, or every account it already uses looks taken.","title":"Exclude Sequence Id"},"description":"Treat accounts already allocated to THIS sequence as available. Pass the sequence being edited, or every account it already uses looks taken."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/deliverability/seg-vendors":{"get":{"tags":["Sequences"],"summary":"List Seg Vendors","description":"The secure-email-gateway vendors a vendor-scoped suppression can name.\n\nDerived from the classifier's own rule table, so every slug listed is one\nthe suppression gate matches. A slug not listed here suppresses nothing.","operationId":"list_seg_vendors_sequencer_deliverability_seg_vendors_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/deliverability/provider-sizing":{"get":{"tags":["Sequences"],"summary":"Get Provider Sizing","description":"How the organisation's whole contact corpus splits across mail providers.\n\nFAIL-OPEN by design: on a backend error it answers all zeros, so all-zero\nmeans \"could not measure\", not \"no contacts\".","operationId":"get_provider_sizing_sequencer_deliverability_provider_sizing_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/contact-ids":{"get":{"tags":["Sequences"],"summary":"List Sequence Contact Ids","description":"EVERY contact id in a sequence matching the filters, unpaginated.\n\nThe companion to the paged `GET /sequences/{id}/contacts`, for \"act on all\nof them\" without walking pages. The app's AG Grid `filterModel` string is a\nUI grid's internal format and is not offered; every app parameter not\noffered here has a default (pinned by a test).","operationId":"list_sequence_contact_ids_sequences__sequence_id__contact_ids_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Free text over name, email and phone.","title":"Search"},"description":"Free text over name, email and phone."},{"name":"state_filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated states to INCLUDE.","title":"State Filter"},"description":"Comma-separated states to INCLUDE."},{"name":"exclude_states","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated states to EXCLUDE; composes with `state_filter`.","title":"Exclude States"},"description":"Comma-separated states to EXCLUDE; composes with `state_filter`."},{"name":"mailbox_filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Allocated mailbox contains.","title":"Mailbox Filter"},"description":"Allocated mailbox contains."},{"name":"phone_allocated_filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Allocated phone number contains.","title":"Phone Allocated Filter"},"description":"Allocated phone number contains."},{"name":"company_filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Company name contains.","title":"Company Filter"},"description":"Company name contains."},{"name":"step_order_filter","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Currently at this step order.","title":"Step Order Filter"},"description":"Currently at this step order."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/stats":{"get":{"tags":["Sequences"],"summary":"Get Sequences Overview","description":"Every sequence with its step and contact counts, plus executed-step totals.\n\n`summary` rolls executed steps up by sequence and step, which is what a\ndashboard across sequences needs - per-sequence detail is\n`GET /sequences/{id}/stats`.","operationId":"get_sequences_overview_sequencer_stats_get","parameters":[{"name":"is_personal","in":"query","required":false,"schema":{"type":"boolean","description":"True: sequences the key owner created. False: the team's SHARED sequences. An organisation key owns none, so `true` answers empty.","default":false,"title":"Is Personal"},"description":"True: sequences the key owner created. False: the team's SHARED sequences. An organisation key owns none, so `true` answers empty."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/calendar/capabilities":{"get":{"tags":["Sequences"],"summary":"Get Sequence Calendar Capabilities","description":"Which calendar features are on for this organisation: `enabled`, `projection` and `actions`.\n\nRead this first: every other calendar route answers 404 while `enabled` is false, and the two actions answer 404\nwhile `actions` is false.","operationId":"get_sequence_calendar_capabilities_sequencer_calendar_capabilities_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceCalendarPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/calendar/org":{"get":{"tags":["Sequences"],"summary":"Get Org Sequence Calendar","description":"The organisation's sequence calendar: what is sending when, grouped by sequence, channel, mailbox or owner.\n\nOnly sequences the key may see (its sequence scope) and lists it may read appear. `scope=personal` is\n\"sequences I own\"; an organisation key has no person behind it and gets 403 - use `team`.","operationId":"get_org_sequence_calendar_sequencer_calendar_org_get","parameters":[{"name":"tz","in":"query","required":false,"schema":{"type":"string","description":"IANA time zone the windows and hours are expressed in.","default":"UTC","title":"Tz"},"description":"IANA time zone the windows and hours are expressed in."},{"name":"start","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Window start (ISO 8601).","title":"Start"},"description":"Window start (ISO 8601)."},{"name":"end","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Window end (ISO 8601).","title":"End"},"description":"Window end (ISO 8601)."},{"name":"group_by","in":"query","required":false,"schema":{"enum":["sequence","channel","mailbox","owner"],"type":"string","default":"sequence","title":"Group By"}},{"name":"granularity","in":"query","required":false,"schema":{"enum":["hour","day"],"type":"string","default":"hour","title":"Granularity"}},{"name":"scope","in":"query","required":false,"schema":{"enum":["personal","team","archived"],"type":"string","description":"`personal` is the sequences the caller owns and needs a personal key; an organisation key uses `team`.","default":"team","title":"Scope"},"description":"`personal` is the sequences the caller owns and needs a personal key; an organisation key uses `team`."},{"name":"show_projected","in":"query","required":false,"schema":{"type":"boolean","description":"Include projected (not yet scheduled) times. 400 `projection_disabled` while off.","default":false,"title":"Show Projected"},"description":"Include projected (not yet scheduled) times. 400 `projection_disabled` while off."},{"name":"show_drafts","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Show Drafts"}},{"name":"statuses","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated sequence statuses.","title":"Statuses"},"description":"Comma-separated sequence statuses."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceCalendarPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/calendar/plan":{"get":{"tags":["Sequences"],"summary":"Get Sequence Calendar Plan","description":"What a sequence will do: its steps with their delays, channels and send window, in the caller's time zone.","operationId":"get_sequence_calendar_plan_sequences__sequence_id__calendar_plan_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"tz","in":"query","required":false,"schema":{"type":"string","description":"IANA time zone the windows and hours are expressed in.","default":"UTC","title":"Tz"},"description":"IANA time zone the windows and hours are expressed in."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceCalendarPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/calendar/when":{"get":{"tags":["Sequences"],"summary":"Get Sequence Calendar When","description":"When a sequence sends: counts per hour or day in a window, sent and upcoming.","operationId":"get_sequence_calendar_when_sequences__sequence_id__calendar_when_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"tz","in":"query","required":false,"schema":{"type":"string","description":"IANA time zone the windows and hours are expressed in.","default":"UTC","title":"Tz"},"description":"IANA time zone the windows and hours are expressed in."},{"name":"start","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Start"}},{"name":"end","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"End"}},{"name":"show_projected","in":"query","required":false,"schema":{"type":"boolean","description":"Include projected (not yet scheduled) times. 400 `projection_disabled` while off.","default":false,"title":"Show Projected"},"description":"Include projected (not yet scheduled) times. 400 `projection_disabled` while off."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceCalendarPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/calendar/when/hour":{"get":{"tags":["Sequences"],"summary":"Get Sequence Calendar Hour","description":"The contacts behind one hour of a sequence's calendar, cursor-paged.","operationId":"get_sequence_calendar_hour_sequences__sequence_id__calendar_when_hour_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"at","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Start of the block (ISO 8601); alias of `start`.","title":"At"},"description":"Start of the block (ISO 8601); alias of `start`."},{"name":"start","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Start of the block (ISO 8601).","title":"Start"},"description":"Start of the block (ISO 8601)."},{"name":"end","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"End of the block; defaults to start + 1 hour.","title":"End"},"description":"End of the block; defaults to start + 1 hour."},{"name":"manual_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"YYYY-MM-DD in `tz`: the manual 'due that day' lane.","title":"Manual Date"},"description":"YYYY-MM-DD in `tz`: the manual 'due that day' lane."},{"name":"tz","in":"query","required":false,"schema":{"type":"string","description":"IANA time zone the windows and hours are expressed in.","default":"UTC","title":"Tz"},"description":"IANA time zone the windows and hours are expressed in."},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Cursor"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"default":50,"title":"Limit"}},{"name":"show_projected","in":"query","required":false,"schema":{"type":"boolean","description":"Include projected (not yet scheduled) times. 400 `projection_disabled` while off.","default":false,"title":"Show Projected"},"description":"Include projected (not yet scheduled) times. 400 `projection_disabled` while off."},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string","minLength":2,"maxLength":100},{"type":"null"}],"description":"Contact name, company or email.","title":"Search"},"description":"Contact name, company or email."},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"One item status value.","title":"Status"},"description":"One item status value."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceCalendarPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/calendar/who":{"get":{"tags":["Sequences"],"summary":"Get Sequence Calendar Who","description":"Who is where in a sequence: each contact with its state, current step and next send time.","operationId":"get_sequence_calendar_who_sequences__sequence_id__calendar_who_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"tz","in":"query","required":false,"schema":{"type":"string","description":"IANA time zone the windows and hours are expressed in.","default":"UTC","title":"Tz"},"description":"IANA time zone the windows and hours are expressed in."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"page","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":1},{"type":"null"}],"description":"1-based page; with `page_size` it overrides offset and limit.","title":"Page"},"description":"1-based page; with `page_size` it overrides offset and limit."},{"name":"page_size","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","maximum":200,"minimum":1},{"type":"null"}],"title":"Page Size"}},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string","minLength":2,"maxLength":100},{"type":"null"}],"title":"Search"}},{"name":"state_filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated contact states; `queued` is the Waiting filter.","title":"State Filter"},"description":"Comma-separated contact states; `queued` is the Waiting filter."},{"name":"exclude_states","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Defaults to `removed`.","title":"Exclude States"},"description":"Defaults to `removed`."},{"name":"show_projected","in":"query","required":false,"schema":{"type":"boolean","description":"Include projected (not yet scheduled) times. 400 `projection_disabled` while off.","default":false,"title":"Show Projected"},"description":"Include projected (not yet scheduled) times. 400 `projection_disabled` while off."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceCalendarPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/contacts/{contact_id}/skip-step":{"post":{"tags":["Sequences"],"summary":"Skip Sequence Contact Step","description":"Skip the contact's current step and move it to the next one.\n\nNeeds write access to the sequence. `expected_step_order` is the double-click guard: when the contact has moved\non, the answer is 409 `step_changed` and nothing is skipped. Records the key's principal as the actor.","operationId":"skip_sequence_contact_step_sequences__sequence_id__contacts__contact_id__skip_step_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ExpectedStepRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceCalendarPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/contacts/{contact_id}/send-now":{"post":{"tags":["Sequences"],"summary":"Send Sequence Contact Step Now","description":"Bring the contact's current step forward so it sends on the next tick, instead of at its scheduled time.\n\nSENDS A REAL MESSAGE to the contact (email, LinkedIn or SMS, by the step's channel), so it needs the `run` tier\non sequences. `expected_step_order` is the double-click guard: 409 `step_changed` when the contact has moved on.","operationId":"send_sequence_contact_step_now_sequences__sequence_id__contacts__contact_id__send_now_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ExpectedStepRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceCalendarPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/sequencer/capacity-health":{"get":{"tags":["Sequences"],"summary":"Get Sequencer Capacity Health","description":"Send volume against mailbox capacity per day for the organisation.\n\nSeparates \"capacity available\" from \"emails actually delivered\", so a silent throughput drop shows. The\norganisation is always the key's. `consecutive_low_days` mirrors the automated alert's trigger.","operationId":"get_sequencer_capacity_health_sequencer_capacity_health_get","parameters":[{"name":"lookback_days","in":"query","required":false,"schema":{"type":"integer","maximum":30,"minimum":1,"description":"Trailing days of send-vs-capacity to return.","default":7,"title":"Lookback Days"},"description":"Trailing days of send-vs-capacity to return."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceCalendarPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/mix-and-match/summary":{"get":{"tags":["Sequences"],"summary":"Get Mix And Match Summary","description":"Is mix-and-match on, and how many idle graduated mailboxes the caller owns. Personal keys only.","operationId":"get_mix_and_match_summary_sequencer_mix_and_match_summary_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceMixAndMatchPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/mix-and-match/preview":{"post":{"tags":["Sequences"],"summary":"Preview Mix And Match","description":"Read-only: the mailboxes suggested for each live sequence at the chosen speed and sender mix.\n\nChanges nothing. Only sequences within the key's sequence scope are included. Personal keys only.","operationId":"preview_mix_and_match_sequencer_mix_and_match_preview_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MixAndMatchPreviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceMixAndMatchPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequencer/mix-and-match/apply":{"post":{"tags":["Sequences"],"summary":"Apply Mix And Match","description":"Attach the selected mailboxes to live sequences, re-checking eligibility first.\n\nChanges which mailboxes send for those sequences, so more mail can go out per day. A mailbox that is no longer\neligible is reported under `skipped`, not attached. Needs write access to each sequence in the key's sequence\nscope. Personal keys only.","operationId":"apply_mix_and_match_sequencer_mix_and_match_apply_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MixAndMatchApplyRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceMixAndMatchPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/inmail/{step_id}/prepare":{"post":{"tags":["Sequences"],"summary":"Prepare Sequence Inmail","description":"Start checking which contacts can receive a free InMail at this step. NEVER sends a message.\n\nReturns the job (`job_id`, `status`); a preparation already running for the step is returned instead of a second\none. Needs write access to the sequence.","operationId":"prepare_sequence_inmail_sequences__sequence_id__inmail__step_id__prepare_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"step_id","in":"path","required":true,"schema":{"type":"string","description":"Step id of the LinkedIn InMail step.","title":"Step Id"},"description":"Step id of the LinkedIn InMail step."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/InmailPrepareRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceInmailPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/inmail/{step_id}":{"get":{"tags":["Sequences"],"summary":"Get Sequence Inmail Readiness","description":"The latest preparation job for the step and each contact's InMail readiness (up to 500 rows).","operationId":"get_sequence_inmail_readiness_sequences__sequence_id__inmail__step_id__get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"step_id","in":"path","required":true,"schema":{"type":"string","description":"Step id of the LinkedIn InMail step.","title":"Step Id"},"description":"Step id of the LinkedIn InMail step."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceInmailPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/inmail/{step_id}/cancel":{"post":{"tags":["Sequences"],"summary":"Cancel Sequence Inmail Preparation","description":"Cancel a queued or running InMail preparation for the step. Messages already prepared are kept.","operationId":"cancel_sequence_inmail_preparation_sequences__sequence_id__inmail__step_id__cancel_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"step_id","in":"path","required":true,"schema":{"type":"string","description":"Step id of the LinkedIn InMail step.","title":"Step Id"},"description":"Step id of the LinkedIn InMail step."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceInmailPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"sequences:delete","x-graph8-lifecycle":"active"}},"/sequencer/related-fields":{"get":{"tags":["Sequences"],"summary":"List Sequence Related Fields","description":"The variables (`related.<definition>.<attribute>`) a step can use from a contact's linked custom-object records.\n\nOnly relationships to contacts whose custom object the credential may read (its own object grants) are offered,\nand only fields it may see. `supported_step_types` lists the step types whose sends fill them. 404 while the\norganisation's `relationships` or `record_context` custom-object switch is off.","operationId":"list_sequence_related_fields_sequencer_related_fields_get","parameters":[{"name":"step_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only the variables a step of this type can use.","title":"Step Type"},"description":"Only the variables a step of this type can use."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceRelatedRecordsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/related-records":{"get":{"tags":["Sequences"],"summary":"List Sequence Related Records","description":"Which linked record each contact's related fields use in this sequence, held-back contacts first.\n\nLimited to relationships the credential may read and to contacts inside its contact read scope.\n`unavailable_fields` names required related fields that no readable relationship provides.","operationId":"list_sequence_related_records_sequences__sequence_id__related_records_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"enum":["pinned","blocked"],"type":"string"},{"type":"null"}],"description":"Only pinned or only held-back contacts.","title":"Status"},"description":"Only pinned or only held-back contacts."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceRelatedRecordsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"},"put":{"tags":["Sequences"],"summary":"Choose Sequence Related Record","description":"Use `record_id` for this contact's related fields of `definition_id` in this sequence. Enrols nobody.\n\nThe record must be a live record of a relationship the credential may read, linked to the contact through it, and\nthe contact must be inside the key's contact scope and belong to the sequence; otherwise 404 \"Record unavailable\".\nA choice replaces any earlier one. Needs write access to the sequence.","operationId":"choose_sequence_related_record_sequences__sequence_id__related_records_put","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ChooseRelatedRecordRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceRelatedRecordsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/related-records/enroll":{"post":{"tags":["Sequences"],"summary":"Choose Sequence Related Record And Enroll","description":"Choose the record (as `PUT`), then enrol exactly this contact in the sequence.\n\nENROLLING STARTS THE CONTACT'S SENDS once the sequence is live, so it needs the launch access that running the\nsequence needs and the `run` tier. Only this contact is enrolled: nobody else on the sequence's list is. Safe to\nretry: an enrolled contact reports `already_enrolled`; `not_enrolled` carries the reason.\n\nNOTE: STARTING a sequence (`POST /sequences/{id}/run`) enrols its WHOLE associated list, every contact on it, not\njust contacts you chose. To enrol a single contact, use this route on a sequence that is already live.","operationId":"choose_sequence_related_record_and_enroll_sequences__sequence_id__related_records_enroll_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ChooseRelatedRecordRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceRelatedRecordsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/sequencer/content/instructions/improve":{"post":{"tags":["Sequences"],"summary":"Improve Step Instruction","description":"Rewrite a step's drafting instruction with a model. RUNS A MODEL per call.\n\nReturns the improved instruction; nothing is saved. Send the current\ninstruction as `old_instruction` so the rewrite keeps its intent.","operationId":"improve_step_instruction_sequencer_content_instructions_improve_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ImproveInstructionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/sequencer/content/voice/test-call":{"post":{"tags":["Sequences"],"summary":"Place Voice Test Call","description":"Place ONE real test call from a voice step. A REAL PHONE RINGS.\n\nThe call runs on the organisation's voice plan and is logged as a dry run,\nnot against any contact or sequence enrolment. Returns the call's\n`room_name`; the outcome arrives through the call logs, not this response.\nSend an `Idempotency-Key` header so a retried request cannot ring twice.","operationId":"place_voice_test_call_sequencer_content_voice_test_call_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VoiceTestCallRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/webhooks/events":{"get":{"tags":["Webhooks"],"summary":"List Webhook Events","description":"List all available webhook event types, each with a category + description.","operationId":"list_webhook_events_webhooks_events_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_WebhookEventResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"webhooks:read","x-graph8-lifecycle":"active"}},"/webhooks":{"get":{"tags":["Webhooks"],"summary":"List Webhooks","description":"List all webhook subscriptions for the organization.","operationId":"list_webhooks_webhooks_get","parameters":[{"name":"is_active","in":"query","required":false,"schema":{"anyOf":[{"type":"boolean"},{"type":"null"}],"description":"Filter by active status","title":"Is Active"},"description":"Filter by active status"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_WebhookResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"webhooks:read","x-graph8-lifecycle":"active"},"post":{"tags":["Webhooks"],"summary":"Create Webhook","description":"Create a new webhook subscription. Returns the secret (only shown once).","operationId":"create_webhook_webhooks_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WebhookCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebhookResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"webhooks:run","x-graph8-lifecycle":"active"}},"/webhooks/{webhook_id}":{"get":{"tags":["Webhooks"],"summary":"Get Webhook","description":"Get webhook subscription details (secret is not returned).","operationId":"get_webhook_webhooks__webhook_id__get","parameters":[{"name":"webhook_id","in":"path","required":true,"schema":{"type":"string","description":"Webhook subscription ID","title":"Webhook Id"},"description":"Webhook subscription ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebhookResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"webhooks:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Webhooks"],"summary":"Update Webhook","description":"Update a webhook subscription.","operationId":"update_webhook_webhooks__webhook_id__patch","parameters":[{"name":"webhook_id","in":"path","required":true,"schema":{"type":"string","description":"Webhook subscription ID","title":"Webhook Id"},"description":"Webhook subscription ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WebhookUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebhookResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"webhooks:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Webhooks"],"summary":"Delete Webhook","description":"Delete a webhook subscription.","operationId":"delete_webhook_webhooks__webhook_id__delete","parameters":[{"name":"webhook_id","in":"path","required":true,"schema":{"type":"string","description":"Webhook subscription ID","title":"Webhook Id"},"description":"Webhook subscription ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"webhooks:delete","x-graph8-lifecycle":"active"}},"/webhooks/{webhook_id}/deliveries":{"get":{"tags":["Webhooks"],"summary":"List Webhook Deliveries","description":"List delivery attempts for a webhook subscription.","operationId":"list_webhook_deliveries_webhooks__webhook_id__deliveries_get","parameters":[{"name":"webhook_id","in":"path","required":true,"schema":{"type":"string","description":"Webhook subscription ID","title":"Webhook Id"},"description":"Webhook subscription ID"},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number","default":1,"title":"Page"},"description":"Page number"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page","default":50,"title":"Limit"},"description":"Items per page"},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by delivery status","title":"Status"},"description":"Filter by delivery status"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_WebhookDeliveryResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"webhooks:read","x-graph8-lifecycle":"active"}},"/webhooks/{webhook_id}/rotate-secret":{"post":{"tags":["Webhooks"],"summary":"Rotate Webhook Secret","description":"Rotate the signing secret for a webhook subscription. Returns the new secret (shown once).","operationId":"rotate_webhook_secret_webhooks__webhook_id__rotate_secret_post","parameters":[{"name":"webhook_id","in":"path","required":true,"schema":{"type":"string","description":"Webhook subscription ID","title":"Webhook Id"},"description":"Webhook subscription ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebhookResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"webhooks:run","x-graph8-lifecycle":"active"}},"/contacts/assert":{"put":{"tags":["Assert / Upsert"],"summary":"Assert Contact","description":"Create or update a contact. Matches by work_email, then linkedin_url.","operationId":"assert_contact_contacts_assert_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContactAssertRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContactAssertResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/assert/batch":{"put":{"tags":["Assert / Upsert"],"summary":"Assert Contacts Batch","description":"Batch create or update up to 100 contacts. Matches by work_email, then linkedin_url.","operationId":"assert_contacts_batch_contacts_assert_batch_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BatchContactAssertRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BatchAssertResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/companies/assert":{"put":{"tags":["Assert / Upsert"],"summary":"Assert Company","description":"Create or update a company. Matches by domain, then linkedin_url.","operationId":"assert_company_companies_assert_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CompanyAssertRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CompanyAssertResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/companies/assert/batch":{"put":{"tags":["Assert / Upsert"],"summary":"Assert Companies Batch","description":"Batch create or update up to 100 companies. Matches by domain, then linkedin_url.","operationId":"assert_companies_batch_companies_assert_batch_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BatchCompanyAssertRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BatchAssertResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/deals/assert":{"put":{"tags":["Assert / Upsert"],"summary":"Assert Deal","description":"Create or update a deal. Matches by name + company_id.\n\nDeliberately NOT wired into the closed-stage gates or the completeness\nrule: assert is the sync-shaped surface (external systems pushing state,\nno human to answer a 400), the same category the internal router excludes\nfor POST /v1/deals/webhook/sync and the CRM pull worker (#15530\n\"Out of scope\"). Only input hygiene applies here: ids must exist and\nclose_date must parse.\n\n#16060: a stage move made here now emits ``deal.stage_changed`` and writes\n``cb_deal_stage_history``, like every other stage writer. ``background_tasks``\nis injected (not a body field, so the request schema is unchanged) and the\npublish is queued only after the session context has exited — a rolled-back\nassert publishes nothing. Because assert is the sync-shaped surface, the\nSAME stage arrives on every tick of the caller's poll loop: the event fires\nonly on an actual transition, never on a re-assert of the current stage.","operationId":"assert_deal_deals_assert_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DealAssertRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DealAssertResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/deals/assert":{"put":{"tags":["Assert / Upsert"],"summary":"Assert Deal Contact","description":"Assert a deal-contact association. Idempotent — no error if already linked.","operationId":"assert_deal_contact_contacts__contact_id__deals_assert_put","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact ID","title":"Contact Id"},"description":"Contact ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DealContactAssertRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/repos":{"post":{"tags":["Repos"],"summary":"Connect Repo","description":"Connect a repository to the organization.","operationId":"connect_repo_repos_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ConnectRepoRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RepoResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"get":{"tags":["Repos"],"summary":"List Repos","description":"List all connected repositories in the organization.","operationId":"list_repos_repos_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (1-indexed)","default":1,"title":"Page"},"description":"Page number (1-indexed)"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page (max 200)","default":50,"title":"Limit"},"description":"Items per page (max 200)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_RepoResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/repos/{repo_id}":{"get":{"tags":["Repos"],"summary":"Get Repo","description":"Get details of a connected repository.","operationId":"get_repo_repos__repo_id__get","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RepoResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Repos"],"summary":"Delete Repo","description":"Disconnect a repository from the organization.","operationId":"delete_repo_repos__repo_id__delete","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/repos/{repo_id}/scan":{"post":{"tags":["Scans"],"summary":"Create Scan","description":"Record pre-computed repository scan results.\n\nThis endpoint does **not** scan a repository server-side — it persists a\nscan produced by the `g8` CLI (or any MCP client that walks the filesystem\nitself). Required fields in the body: ``tech_stack``, ``api_routes``,\n``gtm_readiness``. The server stores the results and links them to the\nrepo so subsequent ``/install`` calls can derive a patch set.","operationId":"create_scan_repos__repo_id__scan_post","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ScanResultsRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ScanResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"search:run","x-graph8-lifecycle":"active"},"get":{"tags":["Scans"],"summary":"Get Scan","description":"Get the latest scan results for a repository.","operationId":"get_scan_repos__repo_id__scan_get","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ScanResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"search:run","x-graph8-lifecycle":"active"}},"/repos/{repo_id}/install":{"post":{"tags":["Install"],"summary":"Generate Install","description":"Generate a patch set describing the changes needed to install the GTM spine.\n\nServer-side only: returns a ``PatchSetResponse`` whose ``patches`` array\ndescribes the file changes (new files, modifications, snippets to add).\n**The caller is responsible for applying them to the local filesystem** —\ntypically the `g8` CLI, but any MCP client can consume the patch array\ndirectly. Follow up with ``POST /install/apply`` once patches are on disk.","operationId":"generate_install_repos__repo_id__install_post","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PatchSetResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"integrations:write","x-graph8-lifecycle":"active"}},"/repos/{repo_id}/install/apply":{"post":{"tags":["Install"],"summary":"Apply Install","description":"Record that the latest patch set has been applied client-side.\n\nThis is a bookkeeping call. The server flips ``patch_sets.status`` from\n``PREVIEW`` to ``APPLIED`` so follow-up scans know the install is live;\nno files are written by this endpoint. The actual filesystem write must\nbe performed by the caller (typically the `g8` CLI) before calling this.","operationId":"apply_install_repos__repo_id__install_apply_post","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ApplyResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"integrations:write","x-graph8-lifecycle":"active"}},"/repos/{repo_id}/install/status":{"get":{"tags":["Install"],"summary":"Get Install Status","description":"Get the latest patch set status for a repository.","operationId":"get_install_status_repos__repo_id__install_status_get","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PatchSetResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/repos/{repo_id}/rollback":{"post":{"tags":["Install"],"summary":"Rollback Install","description":"Rollback the last applied patch set.","operationId":"rollback_install_repos__repo_id__rollback_post","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PatchSetResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"integrations:write","x-graph8-lifecycle":"active"}},"/repos/{repo_id}/streams":{"get":{"tags":["Install"],"summary":"List Streams","description":"List available tracking streams (sites) for this organization.\n\nReturns each stream's ID, user-friendly name (domain or label),\nassociated domains, and write key. The caller should select one\nand pass its `id` to the snippet endpoint.\n\nStreams belong to the organization, not to the repository: every stream\nof the org is listed, and `repo_id` on each one names the connected\nrepository already using it (null when none does). The repository must\nexist in the caller's organization (404 otherwise). The org-level\nequivalent that needs no repository is `GET /streams`.","operationId":"list_streams_repos__repo_id__streams_get","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"page","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":1},{"type":"null"}],"description":"Page number (1-indexed). Omit page and limit to get every stream.","title":"Page"},"description":"Page number (1-indexed). Omit page and limit to get every stream."},{"name":"limit","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","maximum":200,"minimum":1},{"type":"null"}],"description":"Streams per page (max 200). Omit page and limit to get every stream.","title":"Limit"},"description":"Streams per page (max 200). Omit page and limit to get every stream."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_StreamInfoResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/repos/{repo_id}/snippet":{"get":{"tags":["Install"],"summary":"Get Snippet","description":"Get the JavaScript tracking snippet for a connected repository.\n\nIf the repo already has a write key stored, returns the snippet immediately.\nOtherwise, pass `stream_id` (from GET /streams) to select which stream to use.\nThe selected write key is stored on the repo for future lookups.","operationId":"get_snippet_repos__repo_id__snippet_get","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"stream_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Stream ID to use. List available via GET /streams.","title":"Stream Id"},"description":"Stream ID to use. List available via GET /streams."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SnippetResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/repos/{repo_id}/campaigns":{"get":{"tags":["CLI Campaigns"],"summary":"List Campaigns","description":"List campaigns generated for a connected repository.","operationId":"list_campaigns_repos__repo_id__campaigns_get","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number","default":1,"title":"Page"},"description":"Page number"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page","default":50,"title":"Limit"},"description":"Items per page"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"post":{"tags":["CLI Campaigns"],"summary":"Create Campaign","description":"Create a new campaign from scratch.","operationId":"create_campaign_repos__repo_id__campaigns_post","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/developer_api__interfaces__v1__cli_campaigns_router__CampaignCreateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/repos/{repo_id}/campaigns/{campaign_id}":{"get":{"tags":["CLI Campaigns"],"summary":"Get Campaign","description":"Get details of a specific campaign including generated documents.","operationId":"get_campaign_repos__repo_id__campaigns__campaign_id__get","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["CLI Campaigns"],"summary":"Update Campaign","description":"Update campaign content fields (name, brief, hook, persona, etc.).","operationId":"update_campaign_repos__repo_id__campaigns__campaign_id__patch","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/developer_api__interfaces__v1__cli_campaigns_router__CampaignUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/repos/{repo_id}/campaigns/{campaign_id}/documents/{document_id}":{"get":{"tags":["CLI Campaigns"],"summary":"Get Campaign Document","description":"Get full content of a specific campaign document.","operationId":"get_campaign_document_repos__repo_id__campaigns__campaign_id__documents__document_id__get","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document ID","title":"Document Id"},"description":"Document ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/repos/{repo_id}/campaigns/{campaign_id}/launch":{"post":{"tags":["CLI Campaigns"],"summary":"Launch Campaign","description":"Launch a campaign via the sequencer bridge.\n\nSame behaviour as ``POST /api/v1/campaigns/{campaign_id}/launch`` — this\nis the repo-scoped variant used by the CLI. See the GTM router docstring\nfor the full push-then-run flow.\n\nWARNING: begins sending real outreach to real contacts.","operationId":"launch_campaign_repos__repo_id__campaigns__campaign_id__launch_post","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:launch","x-graph8-lifecycle":"active"}},"/pipelines":{"get":{"tags":["CLI Pipelines"],"summary":"List Pipelines","description":"List all deal pipelines for the org, with stages including v2 fields.","operationId":"list_pipelines_pipelines_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_PipelineResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"post":{"tags":["CLI Pipelines"],"summary":"Create Pipeline","description":"Create a new pipeline, auto-seeded with the appropriate target's default stages.","operationId":"create_pipeline_pipelines_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PipelineCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PipelineResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/pipelines/evidence-library":{"get":{"tags":["CLI Pipelines"],"summary":"List Stage Evidence Library","description":"Return the canonical 8 stage evidence keys + human-readable labels.","operationId":"list_stage_evidence_library_pipelines_evidence_library_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/pipelines/{pipeline_id}":{"get":{"tags":["CLI Pipelines"],"summary":"Get Pipeline","description":"Get one pipeline by ID, with stages including v2 fields.","operationId":"get_pipeline_pipelines__pipeline_id__get","parameters":[{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","title":"Pipeline Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PipelineResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"put":{"tags":["CLI Pipelines"],"summary":"Update Pipeline","description":"Rename, retarget, and/or promote a pipeline to default.","operationId":"update_pipeline_pipelines__pipeline_id__put","parameters":[{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","title":"Pipeline Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PipelineUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PipelineResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"delete":{"tags":["CLI Pipelines"],"summary":"Delete Pipeline","description":"Delete a pipeline. Fails if it has deals or is the org's only pipeline.","operationId":"delete_pipeline_pipelines__pipeline_id__delete","parameters":[{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","title":"Pipeline Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/pipelines/{pipeline_id}/stages":{"post":{"tags":["CLI Pipelines"],"summary":"Create Stage","description":"Add a new stage to a pipeline, with v2 checklist + scripts fields.","operationId":"create_stage_pipelines__pipeline_id__stages_post","parameters":[{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","title":"Pipeline Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StageCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PipelineStageResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/pipelines/{pipeline_id}/stages/reorder":{"put":{"tags":["CLI Pipelines"],"summary":"Reorder Stages","description":"Reorder stages by passing the full ordered list of stage IDs.","operationId":"reorder_stages_pipelines__pipeline_id__stages_reorder_put","parameters":[{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","title":"Pipeline Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StageReorderRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_PipelineStageResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/pipelines/{pipeline_id}/stages/{stage_id}":{"put":{"tags":["CLI Pipelines"],"summary":"Update Stage","description":"Update a stage. All parameters optional.","operationId":"update_stage_pipelines__pipeline_id__stages__stage_id__put","parameters":[{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","title":"Pipeline Id"}},{"name":"stage_id","in":"path","required":true,"schema":{"type":"string","title":"Stage Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StageUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PipelineStageResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"delete":{"tags":["CLI Pipelines"],"summary":"Delete Stage","description":"Delete a stage. Fails if it has deals or pipeline would drop below 2 stages.","operationId":"delete_stage_pipelines__pipeline_id__stages__stage_id__delete","parameters":[{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","title":"Pipeline Id"}},{"name":"stage_id","in":"path","required":true,"schema":{"type":"string","title":"Stage Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/pipelines/suggest":{"post":{"tags":["CLI Pipelines"],"summary":"Suggest Pipeline","description":"Generate an AI-suggested pipeline draft grounded in the org's global context.\n\nReturns the draft dict (PipelineSuggestion shape) — does NOT persist.\nCharges credits at the g8_t2 (Sonnet) tier per call. On Anthropic API\nfailure or empty global context, returns a generic target-appropriate\nfallback with `context_sources: []`.","operationId":"suggest_pipeline_pipelines_suggest_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuggestRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/pipelines/from-suggestion":{"post":{"tags":["CLI Pipelines"],"summary":"Create Pipeline From Suggestion","description":"Persist a (possibly edited) PipelineSuggestion as a real pipeline.\n\nValidates evidence keys against STAGE_EVIDENCE_LIBRARY, sanitizes\nchannel_scripts, and creates the pipeline + stages atomically. No\ndedup — the caller is responsible for not posting the same draft twice.","operationId":"create_pipeline_from_suggestion_pipelines_from_suggestion_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Suggestion"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-pages/reporting/overview":{"get":{"tags":["Landing Pages"],"summary":"Get Landing Page Reporting Overview","description":"Landing-page performance: visits, identified people and companies, conversions. FREE.","operationId":"get_landing_page_reporting_overview_landing_pages_reporting_overview_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Look-back window in days.","default":30,"title":"Days"},"description":"Look-back window in days."},{"name":"page_id","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"string"}},{"type":"null"}],"description":"Only these pages. Repeat the parameter.","title":"Page Id"},"description":"Only these pages. Repeat the parameter."},{"name":"source","in":"query","required":false,"schema":{"enum":["all","paid","email","organic","referral","direct"],"type":"string","description":"Traffic source.","default":"all","title":"Source"},"description":"Traffic source."},{"name":"observed_campaign","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"description":"Only this UTM campaign.","title":"Observed Campaign"},"description":"Only this UTM campaign."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/landing-pages/reporting/people":{"get":{"tags":["Landing Pages"],"summary":"List Landing Page Reporting People","description":"The identified PEOPLE who visited, with what they viewed. FREE. Page with `cursor`.","operationId":"list_landing_page_reporting_people_landing_pages_reporting_people_get","parameters":[{"name":"cursor","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Cursor"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":50,"title":"Limit"}},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Look-back window in days.","default":30,"title":"Days"},"description":"Look-back window in days."},{"name":"page_id","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"string"}},{"type":"null"}],"description":"Only these pages. Repeat the parameter.","title":"Page Id"},"description":"Only these pages. Repeat the parameter."},{"name":"source","in":"query","required":false,"schema":{"enum":["all","paid","email","organic","referral","direct"],"type":"string","description":"Traffic source.","default":"all","title":"Source"},"description":"Traffic source."},{"name":"observed_campaign","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"description":"Only this UTM campaign.","title":"Observed Campaign"},"description":"Only this UTM campaign."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/landing-pages/reporting/companies":{"get":{"tags":["Landing Pages"],"summary":"List Landing Page Reporting Companies","description":"The COMPANIES whose people visited. FREE. Page with `cursor`.","operationId":"list_landing_page_reporting_companies_landing_pages_reporting_companies_get","parameters":[{"name":"cursor","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Cursor"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":50,"title":"Limit"}},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Look-back window in days.","default":30,"title":"Days"},"description":"Look-back window in days."},{"name":"page_id","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"string"}},{"type":"null"}],"description":"Only these pages. Repeat the parameter.","title":"Page Id"},"description":"Only these pages. Repeat the parameter."},{"name":"source","in":"query","required":false,"schema":{"enum":["all","paid","email","organic","referral","direct"],"type":"string","description":"Traffic source.","default":"all","title":"Source"},"description":"Traffic source."},{"name":"observed_campaign","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"description":"Only this UTM campaign.","title":"Observed Campaign"},"description":"Only this UTM campaign."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/landing-page-consent/default":{"get":{"tags":["Landing Pages"],"summary":"Get Landing Page Consent Default","description":"The workspace-wide consent gate default. FREE. `consent: null` means none is set.","operationId":"get_landing_page_consent_default_landing_page_consent_default_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"put":{"tags":["Landing Pages"],"summary":"Set Landing Page Consent Default","description":"Set the workspace-wide consent gate default. ADMIN ONLY.\n\nA compliance control for every page that does not override it. Takes\neffect on each page's NEXT publish - already-published HTML is not\nrewritten; `GET /landing-page-consent/pages` shows which pages are stale.\n\nSpends nothing.","operationId":"set_landing_page_consent_default_landing_page_consent_default_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LandingPageConsentConfig"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-page-consent/pages":{"get":{"tags":["Landing Pages"],"summary":"List Landing Page Consent Status","description":"Per published page: is the consent gate ACTUALLY live on it. FREE.\n\nRead from the published HTML, not the settings - `stale_count` is how\nmany pages need a re-publish to pick up the current configuration.","operationId":"list_landing_page_consent_status_landing_page_consent_pages_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/tracking":{"get":{"tags":["Landing Pages"],"summary":"Get Landing Page Tracking","description":"The page's tracking mode, form id, chat widget, consent and conversion goal. FREE.","operationId":"get_landing_page_tracking_landing_pages__landing_page_id__tracking_get","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Landing Pages"],"summary":"Update Landing Page Tracking","description":"Change the page's tracking settings. FREE. Only the fields you send change.\n\nMoving TO `dedicated` goes through `/tracking/provision`; a PATCH to it is\nrejected. Takes effect on the page's next publish.","operationId":"update_landing_page_tracking_landing_pages__landing_page_id__tracking_patch","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LandingPageTrackingPatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/tracking/provision":{"post":{"tags":["Landing Pages"],"summary":"Provision Landing Page Tracking","description":"Give the page its OWN tracking stream and browser key. FREE.\n\nSwitches the page to `dedicated` tracking; takes effect on its next\npublish. The form id label and chat setting are preserved.","operationId":"provision_landing_page_tracking_landing_pages__landing_page_id__tracking_provision_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/tracking/consent":{"delete":{"tags":["Landing Pages"],"summary":"Clear Landing Page Consent Override","description":"Drop the page's own consent settings so it inherits the workspace default.\n\nSpends nothing.","operationId":"clear_landing_page_consent_override_landing_pages__landing_page_id__tracking_consent_delete","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/landing-pages/components":{"get":{"tags":["Landing Pages"],"summary":"List Landing Page Components","description":"UI components extracted from the org's cloned homepage. FREE.\n\nReads what a previous extraction stored. `POST /components/extract` is the\none that re-derives them.","operationId":"list_landing_page_components_landing_pages_components_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/landing-pages/components/extract":{"post":{"tags":["Landing Pages"],"summary":"Extract Landing Page Components","description":"Re-extract components from the cloned homepage. SPENDS CREDIT.\n\nThe same work `GET /components` returns the cached result of, run again on\npurpose - use the GET unless the homepage clone has changed.","operationId":"extract_landing_page_components_landing_pages_components_extract_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/landing-pages/design-system":{"get":{"tags":["Landing Pages"],"summary":"Get Landing Page Design System","description":"The org's colours, type and spacing, as generation uses them. FREE.","operationId":"get_landing_page_design_system_landing_pages_design_system_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/landing-pages/domains":{"get":{"tags":["Landing Pages"],"summary":"List Landing Page Domains","description":"The domains a page can be published on. FREE.\n\nThe org's verified custom domains plus the default hosted domain - the\nvalid values for `domain` on `POST /landing-pages/{id}/publish`.","operationId":"list_landing_page_domains_landing_pages_domains_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/landing-pages/clone-homepage":{"post":{"tags":["Landing Pages"],"summary":"Clone Homepage To Landing Page","description":"Clone the org's homepage into an editable page. SPENDS CREDIT.\n\n`use_vision` is on by default and is the expensive half: it runs a\nmultimodal pass over a screenshot so the clone looks like the original\nrather than like its HTML.","operationId":"clone_homepage_to_landing_page_landing_pages_clone_homepage_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CloneHomepageRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/landing-pages/clone-url":{"post":{"tags":["Landing Pages"],"summary":"Clone Url To Landing Page","description":"Clone ANY public URL into an editable page. SPENDS CREDIT.\n\nIt fetches the URL server-side, so the page has to be publicly reachable -\nthis is not a way to read something behind the caller's own login.","operationId":"clone_url_to_landing_page_landing_pages_clone_url_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CloneUrlRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/landing-pages/clone-html":{"post":{"tags":["Landing Pages"],"summary":"Clone Html To Landing Page","description":"Clone from raw source the caller already holds. SPENDS CREDIT.\n\n`use_vision` defaults OFF here and ON for `/clone-url`, which is the app's\nasymmetry and a real one: there is no live page to screenshot.","operationId":"clone_html_to_landing_page_landing_pages_clone_html_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CloneHtmlRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/landing-pages/ensure-base-template":{"post":{"tags":["Landing Pages"],"summary":"Ensure Landing Page Base Template","description":"Return the org's base template, creating it if there is none.\n\nIDEMPOTENT: it returns the existing template when one exists and spends\nnothing. It SPENDS CREDIT only on the first call for an org, where it\nclones the homepage to make one.","operationId":"ensure_landing_page_base_template_landing_pages_ensure_base_template_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/landing-pages":{"get":{"tags":["Landing Pages"],"summary":"List Landing Pages","description":"Every landing page in the org. FREE.","operationId":"list_landing_pages_landing_pages_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by page status (draft, published, ...).","title":"Status"},"description":"Filter by page status (draft, published, ...)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"post":{"tags":["Landing Pages"],"summary":"Create Landing Page","description":"Create a landing page. SPENDS CREDIT unless `generate` is false.\n\n`generate` defaults TRUE, matching Studio, and that default is the whole\ncost of this call: it runs the full copy-and-layout pass. Send\n`generate: false` for an empty page you will fill with `/clone-url`,\n`/import-html` or the deterministic edit routes.\n\n`created_by` is the API key's own principal. An organisation key records\nthe key's identity rather than a person's, which is the honest answer -\nthere is no human behind it.","operationId":"create_landing_page_landing_pages_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateLandingPageRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}":{"get":{"tags":["Landing Pages"],"summary":"Get Landing Page","description":"One page with its full detail, including its HTML. FREE.","operationId":"get_landing_page_landing_pages__landing_page_id__get","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Landing Pages"],"summary":"Update Landing Page","description":"Metadata only - name, slug, description, settings. FREE.\n\nNothing here touches the page's HTML. The edit routes do that.","operationId":"update_landing_page_landing_pages__landing_page_id__patch","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateLandingPageRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Landing Pages"],"summary":"Delete Landing Page","description":"Delete a landing page. Unpublish it first if it is live.\n\nSpends nothing.","operationId":"delete_landing_page_landing_pages__landing_page_id__delete","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/generate-seo-metadata":{"post":{"tags":["Landing Pages"],"summary":"Generate Landing Page Seo Metadata","description":"Derive title, description and keywords from the page. SPENDS CREDIT.","operationId":"generate_landing_page_seo_metadata_landing_pages__landing_page_id__generate_seo_metadata_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/sections/{section_idx}":{"patch":{"tags":["Landing Pages"],"summary":"Update Landing Page Section","description":"Replace one section's content block. FREE - no model runs.\n\nSections-mode pages only. A freeform page has no section array; use\n`/replace-html` or `/set-text` on those.","operationId":"update_landing_page_section_landing_pages__landing_page_id__sections__section_idx__patch","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"section_idx","in":"path","required":true,"schema":{"type":"integer","minimum":0,"description":"Zero-based section index.","title":"Section Idx"},"description":"Zero-based section index."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateSectionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/edit":{"post":{"tags":["Landing Pages"],"summary":"Edit Landing Page With Chat","description":"Edit the page from a natural-language instruction. SPENDS CREDIT.\n\nThe buffered form of the Studio chat edit. The streaming one is\ndeliberately not published - see the module docstring.","operationId":"edit_landing_page_with_chat_landing_pages__landing_page_id__edit_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EditWithChatRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/save-as-page":{"post":{"tags":["Landing Pages"],"summary":"Save Landing Page Template As Page","description":"Copy an org TEMPLATE into a new editable page. FREE.\n\nThe template is untouched, which is the difference from\n`/promote-to-page`: that one MOVES the template out of the template list.","operationId":"save_landing_page_template_as_page_landing_pages__landing_page_id__save_as_page_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/promote-to-page":{"post":{"tags":["Landing Pages"],"summary":"Promote Landing Page Template","description":"Turn a template INTO a page. FREE.\n\nIt MOVES the row rather than copying it - the template stops being a\ntemplate. `/save-as-page` is the copying version, and `/demote-to-template`\nis the inverse of this one.","operationId":"promote_landing_page_template_landing_pages__landing_page_id__promote_to_page_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/demote-to-template":{"post":{"tags":["Landing Pages"],"summary":"Demote Landing Page To Template","description":"Move a saved page back into the template list. FREE. Inverse of promote.","operationId":"demote_landing_page_to_template_landing_pages__landing_page_id__demote_to_template_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/approve-template":{"patch":{"tags":["Landing Pages"],"summary":"Approve Landing Page Template","description":"Move a generated template from pending-approval to completed. FREE.","operationId":"approve_landing_page_template_landing_pages__landing_page_id__approve_template_patch","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/convert-to-freeform":{"post":{"tags":["Landing Pages"],"summary":"Convert Landing Page To Freeform","description":"Flatten a sections-mode page into freeform HTML. FREE.\n\nONE-WAY: there is no convert-back, and `PATCH /sections/{idx}` stops\napplying to the page afterwards.","operationId":"convert_landing_page_to_freeform_landing_pages__landing_page_id__convert_to_freeform_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/update-html":{"post":{"tags":["Landing Pages"],"summary":"Update Landing Page Html","description":"Save raw HTML for a freeform page. FREE - the code-editor save.","operationId":"update_landing_page_html_landing_pages__landing_page_id__update_html_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateHtmlRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/update-text":{"post":{"tags":["Landing Pages"],"summary":"Update Landing Page Text","description":"Set one element's inner HTML directly. FREE.\n\n`new_html`, not `new_text`: this one accepts markup. `/set-text` is the\ntext-only sibling and is the safer of the two.","operationId":"update_landing_page_text_landing_pages__landing_page_id__update_text_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateTextRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/set-text":{"post":{"tags":["Landing Pages"],"summary":"Set Landing Page Text","description":"Set the VISIBLE TEXT of one element. FREE - markup is preserved.","operationId":"set_landing_page_text_landing_pages__landing_page_id__set_text_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LandingPageSetTextRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/set-media-edit":{"post":{"tags":["Landing Pages"],"summary":"Set Landing Page Media","description":"Point an `<img>` / `<video>` at a URL, or remove it. FREE.\n\n`remove: true` DELETES the element. It is the one destructive field in the\nbody and it is not implied by any other field.\n\nThis is the API-shaped alternative to the multipart upload route, which is\ndeliberately not published: host the asset (the image library will do it),\nthen send its URL here.","operationId":"set_landing_page_media_landing_pages__landing_page_id__set_media_edit_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LandingPageSetMediaEditRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/replace-html":{"post":{"tags":["Landing Pages"],"summary":"Replace Landing Page Html","description":"Persist a whole-page snapshot. FREE.\n\nWholesale: whatever is not in `html` is gone. It creates a restorable\nversion first, which is the only thing standing between a bad snapshot and\na lost page.","operationId":"replace_landing_page_html_landing_pages__landing_page_id__replace_html_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ReplaceHtmlRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/import-html":{"post":{"tags":["Landing Pages"],"summary":"Import Landing Page Html","description":"Import externally edited HTML into the draft. FREE.\n\n`commit` defaults FALSE, which makes the default call a DRY RUN reporting\nwhat would change. Send `commit: true` to write it.","operationId":"import_landing_page_html_landing_pages__landing_page_id__import_html_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ImportHtmlRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/rewrite-text":{"post":{"tags":["Landing Pages"],"summary":"Rewrite Landing Page Text","description":"Rewrite one element's text with AI. SPENDS CREDIT.\n\nText only - no HTML is generated - which makes it the cheapest AI edit\nhere and the right one for a copy change.","operationId":"rewrite_landing_page_text_landing_pages__landing_page_id__rewrite_text_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LandingPageRewriteTextRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/edit-element":{"post":{"tags":["Landing Pages"],"summary":"Edit Landing Page Element","description":"Edit ONE element by CSS selector with AI. SPENDS CREDIT.\n\nFreeform pages. Narrower and cheaper than `/edit-page`, which rewrites the\nwhole document.","operationId":"edit_landing_page_element_landing_pages__landing_page_id__edit_element_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EditElementRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/edit-page":{"post":{"tags":["Landing Pages"],"summary":"Edit Landing Page Whole","description":"Rewrite the WHOLE page from one instruction. SPENDS CREDIT.\n\nThe most expensive edit on this router - it puts the entire document\nthrough the model. Reach for `/edit-element` or `/rewrite-text` first.","operationId":"edit_landing_page_whole_landing_pages__landing_page_id__edit_page_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EditWithChatRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/ai-review":{"post":{"tags":["Landing Pages"],"summary":"Review Landing Page","description":"Run a review pass and return findings. SPENDS CREDIT.\n\nIt CHANGES NOTHING - the findings are applied by\n`/ai-review/apply` (free, deterministic) or `/ai-review/fix-with-ai`\n(another model pass). Reviewing is still a spend even though it is\nread-only against the page, which is why it is not tiered as a read.","operationId":"review_landing_page_landing_pages__landing_page_id__ai_review_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/AIReviewRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/ai-review/apply":{"post":{"tags":["Landing Pages"],"summary":"Apply Landing Page Review Findings","description":"Apply findings DETERMINISTICALLY. FREE - no model runs.\n\nPrefer this to `/fix-with-ai` for anything the review already gave an\nexact replacement for; it costs nothing and cannot invent a change.","operationId":"apply_landing_page_review_findings_landing_pages__landing_page_id__ai_review_apply_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AIReviewApplyRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/ai-review/fix-with-ai":{"post":{"tags":["Landing Pages"],"summary":"Fix Landing Page Finding With Ai","description":"Send ONE finding to the edit engine. SPENDS CREDIT, per finding.\n\nOne call per finding: fixing ten findings is ten passes, not one.","operationId":"fix_landing_page_finding_with_ai_landing_pages__landing_page_id__ai_review_fix_with_ai_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AIReviewFixWithAIRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/publish":{"post":{"tags":["Landing Pages"],"summary":"Publish Landing Page","description":"Deploy the page to a PUBLIC URL. Real people can reach it immediately.\n\nSpends no credit, but it is the outward-facing operation on this router\nand is tiered and gated accordingly - `CAMPAIGNS_LAUNCH`, the same\npermission the app requires, re-declared on this route because the app's\nown `Depends` gate does not run on a direct call.\n\nOmit the body to publish at the page's own slug on the org's default\ndomain. `override: true` takes a URL that is already bound to a DIFFERENT\npage, and that page stops serving at it.\n\nSpends nothing.","operationId":"publish_landing_page_landing_pages__landing_page_id__publish_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/PublishLandingPageRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/unpublish":{"post":{"tags":["Landing Pages"],"summary":"Unpublish Landing Page","description":"Take the page OFF the internet. Every URL it served stops resolving.\n\nVisitors and any ad or email pointing at it get a 404 from this moment.\nLaunch-gated for the same reason publishing is.\n\nSpends nothing.","operationId":"unpublish_landing_page_landing_pages__landing_page_id__unpublish_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/bindings":{"get":{"tags":["Landing Pages"],"summary":"List Landing Page Bindings","description":"Every URL this page is currently served at. FREE.\n\nOne page can be bound to several. Read this before unpublishing, because\nunpublishing drops all of them at once.","operationId":"list_landing_page_bindings_landing_pages__landing_page_id__bindings_get","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Landing Pages"],"summary":"Remove Landing Page Binding","description":"Stop serving the page at ONE URL. The others keep working.\n\nThe surgical version of `/unpublish`, and outward-facing for the same\nreason: that URL 404s from this moment. Launch-gated.\n\nSpends nothing.","operationId":"remove_landing_page_binding_landing_pages__landing_page_id__bindings_delete","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"hostname","in":"query","required":true,"schema":{"type":"string","description":"The host to stop serving this page at.","title":"Hostname"},"description":"The host to stop serving this page at."},{"name":"path","in":"query","required":false,"schema":{"type":"string","description":"The path under that host. Defaults to the root.","default":"/","title":"Path"},"description":"The path under that host. Defaults to the root."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/manifest":{"get":{"tags":["Landing Pages"],"summary":"Get Landing Page Manifest","description":"The element manifest. FREE.\n\nThe SOURCE of the `element_id` values `/set-text`, `/update-text` and\n`/set-media-edit` accept. Read it first - an id invented by hand addresses\nnothing, and `/import-html` with `reassign_g8_ids` invalidates every id you\nare holding.","operationId":"get_landing_page_manifest_landing_pages__landing_page_id__manifest_get","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/anchors":{"get":{"tags":["Landing Pages"],"summary":"List Landing Page Anchors","description":"The page's named anchors. FREE - the valid targets for an in-page link.","operationId":"list_landing_page_anchors_landing_pages__landing_page_id__anchors_get","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/status":{"get":{"tags":["Landing Pages"],"summary":"Get Landing Page Status","description":"Generation progress for one page. FREE.\n\nThe poll target after `POST /landing-pages` or a clone: generation runs in\nthe background and this says whether the page is still being written.","operationId":"get_landing_page_status_landing_pages__landing_page_id__status_get","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/export":{"get":{"tags":["Landing Pages"],"summary":"Export Landing Page","description":"The page as one self-contained HTML document. FREE.\n\nFor hosting the page yourself: styles and assets are inlined, so the\ndocument renders without graph8.","operationId":"export_landing_page_landing_pages__landing_page_id__export_get","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/versions":{"get":{"tags":["Landing Pages"],"summary":"List Landing Page Versions","description":"The page's saved versions, newest first. FREE.\n\nEvery edit route snapshots the page before it changes it; these are the\nsnapshots `POST .../versions/{version_num}/restore` can roll back to.","operationId":"list_landing_page_versions_landing_pages__landing_page_id__versions_get","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/versions/{version_num}/restore":{"post":{"tags":["Landing Pages"],"summary":"Restore Landing Page Version","description":"Roll the page back to a saved version. FREE - no model runs.\n\nThe current state is snapshotted first, so a restore is itself undoable.\nA PUBLISHED page keeps serving its published HTML until it is published\nagain.","operationId":"restore_landing_page_version_landing_pages__landing_page_id__versions__version_num__restore_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"version_num","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Version number, from `GET .../versions`.","title":"Version Num"},"description":"Version number, from `GET .../versions`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/conversation":{"get":{"tags":["Landing Pages"],"summary":"Get Landing Page Conversation","description":"The AI edit conversation recorded against this page. FREE.\n\nEvery `/edit`, `/edit-element` and `/edit-page` instruction and the\nassistant's reply, in order.","operationId":"get_landing_page_conversation_landing_pages__landing_page_id__conversation_get","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/preview":{"get":{"tags":["Landing Pages"],"summary":"Create Landing Page Preview Link","description":"Mint a time-limited preview link for an UNPUBLISHED page. FREE.\n\nAnyone holding the link can view the draft until it expires - share it\nfor review, not publicly. Nothing is published.","operationId":"create_landing_page_preview_link_landing_pages__landing_page_id__preview_get","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/landing-pages/{landing_page_id}/duplicate":{"post":{"tags":["Landing Pages"],"summary":"Duplicate Landing Page Template","description":"Copy a Brand Kit TEMPLATE as another template. FREE - no model runs.\n\nOnly an org template can be duplicated (400 otherwise); to turn a\ntemplate into an editable page use `/save-as-page`. `created_by` is the\nAPI key's own principal.","operationId":"duplicate_landing_page_template_landing_pages__landing_page_id__duplicate_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"Landing page id.","title":"Landing Page Id"},"description":"Landing page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DuplicateTemplateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/ad-creatives/specs":{"get":{"tags":["Ad Creatives"],"summary":"Get Ad Creative Specs","description":"Every platform and ad format the generator supports. FREE.\n\nThe SOURCE of the `platform` / `ad_format` values `POST /ad-creatives`\naccepts, and of the `formats` list `/size-set` takes. Read it first: an\ninvented format is rejected inside the service, after the request has\nalready been accepted.","operationId":"get_ad_creative_specs_ad_creatives_specs_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/ad-creatives/concepts":{"post":{"tags":["Ad Creatives"],"summary":"Generate Ad Concepts","description":"Three to six creative DIRECTIONS to react to. SPENDS CREDIT - one pass.\n\nStateless: nothing is persisted, and no creative is generated. This is the\ncheap step to take BEFORE `POST /ad-creatives`, which spends a copy pass\nand an image pass per creative - reacting to four directions here costs a\nfraction of generating four ads and discarding three.","operationId":"generate_ad_concepts_ad_creatives_concepts_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ConceptsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/ad-creatives":{"get":{"tags":["Ad Creatives"],"summary":"List Ad Creatives","description":"The org's ad creatives. FREE.\n\n`templates=true` switches the collection entirely: it returns the reusable\ntemplates, not a filtered view of the working creatives. The two sets do\nnot overlap.","operationId":"list_ad_creatives_ad_creatives_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by status.","title":"Status"},"description":"Filter by status."},{"name":"platform","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter to one platform.","title":"Platform"},"description":"Filter to one platform."},{"name":"ad_format","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter to one format - landscape, square, portrait, ...","title":"Ad Format"},"description":"Filter to one format - landscape, square, portrait, ..."},{"name":"templates","in":"query","required":false,"schema":{"type":"boolean","description":"List reusable TEMPLATES instead of working creatives.","default":false,"title":"Templates"},"description":"List reusable TEMPLATES instead of working creatives."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"post":{"tags":["Ad Creatives"],"summary":"Create Ad Creative","description":"Generate an ad creative. SPENDS CREDIT - a copy pass and an image pass.\n\nASYNCHRONOUS: the row is committed as `generating` and returned\nimmediately; the copy and the image land afterwards. Poll\n`GET /ad-creatives/{id}` until its status settles.\n\n`image_source: \"library\"` with a `library_image_id` skips the image pass\nand is materially cheaper. `image_source: \"ai\"` is the default and is what\nthe cost of this call mostly is.","operationId":"create_ad_creative_ad_creatives_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateAdCreativeRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/ad-creatives/batch":{"post":{"tags":["Ad Creatives"],"summary":"Create Ad Creative Set","description":"Generate a persona x platform matrix of creatives. SPENDS CREDIT, per cell.\n\nUp to 24 full creatives (copy pass + image pass each) in one call - the\nlargest spend on this router. Every row is committed as `generating`\nbefore any generation starts; poll each creative's `/status`.","operationId":"create_ad_creative_set_ad_creatives_batch_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateAdCreativeSetRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/ad-creatives/video-templates":{"get":{"tags":["Ad Creatives"],"summary":"List Video Ad Templates","description":"The video ad templates. FREE - the valid `template_id` values for `POST /ad-creatives/video`.","operationId":"list_video_ad_templates_ad_creatives_video_templates_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/ad-creatives/video":{"post":{"tags":["Ad Creatives"],"summary":"Create Video Ad Creative","description":"Assemble generated clips into a video ad on a template. FREE.\n\nThe footage was paid for when each clip was generated; this renders the\nstoryboard (1-5 shots) and the template's copy slots into one creative.","operationId":"create_video_ad_creative_ad_creatives_video_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateVideoCreativeRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/ad-creatives/video/clips/prompt-enhance":{"post":{"tags":["Ad Creatives"],"summary":"Enhance Video Clip Prompt","description":"Write one generation prompt from the structured shot form. SPENDS CREDIT (small).\n\nA model rewrites the form into the prompt `POST /ad-creatives/video/clips`\ntakes as `prompt_final`; the response carries `credits_charged`.","operationId":"enhance_video_clip_prompt_ad_creatives_video_clips_prompt_enhance_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VideoPromptEnhanceRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/ad-creatives/video/clips":{"post":{"tags":["Ad Creatives"],"summary":"Generate Video Clip","description":"Generate one video clip. SPENDS CREDIT - priced per second of footage.\n\nASYNCHRONOUS: the clip is queued and returned at once; poll\n`GET /ad-creatives/video/clips/{clip_id}`. An org can have only a few\nclips generating at a time - over that cap is a 429.","operationId":"generate_video_clip_ad_creatives_video_clips_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/GenerateVideoClipRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"},"get":{"tags":["Ad Creatives"],"summary":"List Video Clips","description":"The org's generated video clips. FREE.","operationId":"list_video_clips_ad_creatives_video_clips_get","parameters":[{"name":"creative_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only the clips attached to this creative.","title":"Creative Id"},"description":"Only the clips attached to this creative."},{"name":"include_discarded","in":"query","required":false,"schema":{"type":"boolean","description":"Include clips you discarded.","default":false,"title":"Include Discarded"},"description":"Include clips you discarded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/ad-creatives/video/clips/{clip_id}":{"get":{"tags":["Ad Creatives"],"summary":"Get Video Clip","description":"One clip and its generation status. FREE - the poll target for clip generation.","operationId":"get_video_clip_ad_creatives_video_clips__clip_id__get","parameters":[{"name":"clip_id","in":"path","required":true,"schema":{"type":"string","description":"Video clip id.","title":"Clip Id"},"description":"Video clip id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Ad Creatives"],"summary":"Discard Video Clip","description":"Discard a clip. FREE, and NOT a refund - the footage was already paid for.","operationId":"discard_video_clip_ad_creatives_video_clips__clip_id__delete","parameters":[{"name":"clip_id","in":"path","required":true,"schema":{"type":"string","description":"Video clip id.","title":"Clip Id"},"description":"Video clip id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/ad-creatives/video/clips/{clip_id}/regenerate":{"post":{"tags":["Ad Creatives"],"summary":"Regenerate Video Clip","description":"Generate the clip again from the same prompt. SPENDS CREDIT - a full new generation.","operationId":"regenerate_video_clip_ad_creatives_video_clips__clip_id__regenerate_post","parameters":[{"name":"clip_id","in":"path","required":true,"schema":{"type":"string","description":"Video clip id.","title":"Clip Id"},"description":"Video clip id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/ad-creatives/video/clips/{clip_id}/extend":{"post":{"tags":["Ad Creatives"],"summary":"Extend Video Clip","description":"Generate more footage continuing this clip. SPENDS CREDIT - priced per added second.","operationId":"extend_video_clip_ad_creatives_video_clips__clip_id__extend_post","parameters":[{"name":"clip_id","in":"path","required":true,"schema":{"type":"string","description":"Video clip id.","title":"Clip Id"},"description":"Video clip id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/ad-creatives/video/clips/{clip_id}/continue":{"post":{"tags":["Ad Creatives"],"summary":"Continue Video Clip","description":"Generate the NEXT shot from this clip's last frame, with a new prompt. SPENDS CREDIT.","operationId":"continue_video_clip_ad_creatives_video_clips__clip_id__continue_post","parameters":[{"name":"clip_id","in":"path","required":true,"schema":{"type":"string","description":"Video clip id.","title":"Clip Id"},"description":"Video clip id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContinueVideoClipRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}":{"get":{"tags":["Ad Creatives"],"summary":"Get Ad Creative","description":"One creative, with its copy, its image and its generation status. FREE.","operationId":"get_ad_creative_ad_creatives__creative_id__get","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Ad Creatives"],"summary":"Update Ad Creative","description":"Edit the copy by hand. FREE - no model runs.\n\nUse this rather than `/rewrite-field` when you already know the words.","operationId":"update_ad_creative_ad_creatives__creative_id__patch","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateAdCreativeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Ad Creatives"],"summary":"Delete Ad Creative","description":"Delete a creative and its revisions.\n\n`ads:edit`, not `ads:delete` - the app's own gate, kept rather than\ninvented, because inventing a stricter one here would refuse callers the\napp accepts.\n\nSpends nothing.","operationId":"delete_ad_creative_ad_creatives__creative_id__delete","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/save-as-template":{"post":{"tags":["Ad Creatives"],"summary":"Save Ad Creative As Template","description":"Clone a finished creative as a reusable template. FREE.\n\nA COPY - the original creative is untouched, and the template appears in\n`GET /ad-creatives?templates=true` rather than in the main list.","operationId":"save_ad_creative_as_template_ad_creatives__creative_id__save_as_template_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/image-elements":{"get":{"tags":["Ad Creatives"],"summary":"List Ad Creative Image Elements","description":"Every editable text element inside the image, with its geometry. FREE.\n\nThe SOURCE of the `index` that `POST /{id}/image-element` takes. The\nindices are positional and a regenerate reshuffles them, so re-read this\nafter any call that changes the image.","operationId":"list_ad_creative_image_elements_ad_creatives__creative_id__image_elements_get","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/image-element":{"post":{"tags":["Ad Creatives"],"summary":"Edit Ad Creative Image Element","description":"Change one text element in the image. FREE - no model runs.\n\nDeterministic: it rewrites the SVG. Send at least one of `text`, `fill` or\n`font_size`; `index` comes from `GET /{id}/image-elements`.","operationId":"edit_ad_creative_image_element_ad_creatives__creative_id__image_element_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EditImageElementRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/reskin":{"post":{"tags":["Ad Creatives"],"summary":"Reskin Ad Creative","description":"Swap the creative's palette. FREE - deterministic colour replacement.\n\nBrand colours only. Nothing is regenerated, so the layout and the copy are\nbyte-identical afterwards.","operationId":"reskin_ad_creative_ad_creatives__creative_id__reskin_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ReskinRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/set-image":{"post":{"tags":["Ad Creatives"],"summary":"Set Ad Creative Image","description":"Point the creative at an image already in the library. FREE.\n\nThe API-shaped alternative to the multipart upload route: put the file in\nthe image library, then reference it here by id.","operationId":"set_ad_creative_image_ad_creatives__creative_id__set_image_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetImageRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/set-image-focus":{"post":{"tags":["Ad Creatives"],"summary":"Set Ad Creative Image Focus","description":"Move the crop focal point. FREE.\n\n0-1 in each axis, 0.5/0.5 being the centre. It decides what survives the\ncrop in every OTHER format the creative is rendered at.","operationId":"set_ad_creative_image_focus_ad_creatives__creative_id__set_image_focus_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetImageFocusRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/revisions":{"get":{"tags":["Ad Creatives"],"summary":"List Ad Creative Revisions","description":"The creative's snapshots. FREE - the `index` values restore takes.","operationId":"list_ad_creative_revisions_ad_creatives__creative_id__revisions_get","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/restore-revision":{"post":{"tags":["Ad Creatives"],"summary":"Restore Ad Creative Revision","description":"Roll the creative back to a snapshot. FREE, and REVERSIBLE.\n\nThe restore is itself snapshotted first, so restoring the wrong revision\nis undone by restoring the one this call just created.","operationId":"restore_ad_creative_revision_ad_creatives__creative_id__restore_revision_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RestoreRevisionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/persona-lens":{"post":{"tags":["Ad Creatives"],"summary":"Read Ad Creative Through Persona","description":"Critique the ad through a buyer persona's eyes. SPENDS CREDIT.\n\nREAD-ONLY against the creative - it returns a critique and changes\nnothing - but a model runs, so it still costs. That is why it is not\ntiered as a read.","operationId":"read_ad_creative_through_persona_ad_creatives__creative_id__persona_lens_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonaLensRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/image-edit-at-point":{"post":{"tags":["Ad Creatives"],"summary":"Edit Ad Creative Image At Point","description":"Pin a point on the image and say what changes there. SPENDS CREDIT.\n\nAn image model runs. `/image-element` is the free, deterministic way to\nchange TEXT in the image - reach for that first.","operationId":"edit_ad_creative_image_at_point_ad_creatives__creative_id__image_edit_at_point_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ImagePointEditRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/size-set":{"post":{"tags":["Ad Creatives"],"summary":"Create Ad Creative Size Set","description":"Fan one creative out into the platform's other formats. SPENDS CREDIT.\n\nONE PASS PER FORMAT, so the cost scales with how many you ask for. Copy is\nlocked verbatim; only the layout and the crop change. Omit `formats` and\nyou get the platform's FULL set, which is the most expensive call on this\nrouter - name the formats you actually need.\n\nAsynchronous: the rows appear immediately and fill in afterwards.","operationId":"create_ad_creative_size_set_ad_creatives__creative_id__size_set_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/SizeSetRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/regenerate-copy":{"post":{"tags":["Ad Creatives"],"summary":"Regenerate Ad Creative Copy","description":"Regenerate ALL the copy. SPENDS CREDIT, and DISCARDS the current text.\n\nThere is no instruction to steer it - it re-runs the original prompt. Use\n`/rewrite-field` to change one field with direction, or `PATCH` to set the\nwords yourself for nothing.","operationId":"regenerate_ad_creative_copy_ad_creatives__creative_id__regenerate_copy_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/regenerate-image":{"post":{"tags":["Ad Creatives"],"summary":"Regenerate Ad Creative Image","description":"Regenerate the image. SPENDS CREDIT - a full image pass.\n\nThe previous image is snapshotted into the revision list first, so it is\nrecoverable through `/restore-revision`.","operationId":"regenerate_ad_creative_image_ad_creatives__creative_id__regenerate_image_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/rewrite-field":{"post":{"tags":["Ad Creatives"],"summary":"Rewrite Ad Creative Field","description":"Rewrite ONE copy field with an instruction. SPENDS CREDIT.\n\nThe cheap, steerable alternative to `/regenerate-copy`: it touches one\nfield and leaves the rest alone.","operationId":"rewrite_ad_creative_field_ad_creatives__creative_id__rewrite_field_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RewriteFieldRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/ai-review":{"post":{"tags":["Ad Creatives"],"summary":"Review Ad Creative","description":"Review the creative and return findings. SPENDS CREDIT.\n\n`deep` defaults FALSE here and TRUE on the landing-page review. That is\nthe app's own asymmetry and it is preserved rather than smoothed over -\nthe two passes cost differently, and quietly changing either default would\nmake the same call behave differently through the API than in Studio.","operationId":"review_ad_creative_ad_creatives__creative_id__ai_review_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/AdAIReviewRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/ai-review/apply":{"post":{"tags":["Ad Creatives"],"summary":"Apply Ad Creative Review Findings","description":"Apply review findings DETERMINISTICALLY. FREE - no model runs.","operationId":"apply_ad_creative_review_findings_ad_creatives__creative_id__ai_review_apply_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApplyFindingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/move-to-gallery":{"post":{"tags":["Ad Creatives"],"summary":"Move Ad Creative To Gallery","description":"Move the creative out of drafts and into the GALLERY.\n\n`ads:launch`, which the app's own permission table marks CRITICAL - the\ngallery is what the ad-platform surface picks from, so this is the step\nthat makes a creative eligible to go live and start spending the\ncustomer's advertising budget. Everything else on this router is\n`ads:view` / `ads:create` / `ads:edit`.\n\n`/move-to-draft` is the inverse and needs only `ads:edit`, matching the\napp: taking a creative back out of the gallery is not the consequential\ndirection.\n\nSpends nothing.","operationId":"move_ad_creative_to_gallery_ad_creatives__creative_id__move_to_gallery_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/move-to-draft":{"post":{"tags":["Ad Creatives"],"summary":"Move Ad Creative To Draft","description":"Take the creative back out of the gallery. Inverse of move-to-gallery.\n\nSpends nothing.","operationId":"move_ad_creative_to_draft_ad_creatives__creative_id__move_to_draft_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/status":{"get":{"tags":["Ad Creatives"],"summary":"Get Ad Creative Status","description":"Just the generation status of one creative. FREE - the cheap poll target.","operationId":"get_ad_creative_status_ad_creatives__creative_id__status_get","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/retry":{"post":{"tags":["Ad Creatives"],"summary":"Retry Ad Creative Generation","description":"Re-run a FAILED generation. SPENDS CREDIT - the copy and image passes run again.","operationId":"retry_ad_creative_generation_ad_creatives__creative_id__retry_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/chat-edit":{"post":{"tags":["Ad Creatives"],"summary":"Chat Edit Ad Creative","description":"Edit the creative with a natural-language instruction. SPENDS CREDIT.\n\nA model rewrites the copy (and, when asked, the image); the previous state\nis snapshotted first, so `/restore-revision` can undo it.","operationId":"chat_edit_ad_creative_ad_creatives__creative_id__chat_edit_post","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AdCreativeChatEditRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/ad-creatives/{creative_id}/conversation":{"get":{"tags":["Ad Creatives"],"summary":"Get Ad Creative Conversation","description":"The chat-edit conversation recorded against this creative. FREE.","operationId":"get_ad_creative_conversation_ad_creatives__creative_id__conversation_get","parameters":[{"name":"creative_id","in":"path","required":true,"schema":{"type":"string","description":"Ad creative id.","title":"Creative Id"},"description":"Ad creative id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/content/calendar":{"get":{"tags":["Content"],"summary":"Get Content Calendar","description":"Everything scheduled in a date window, across all five lanes. FREE.\n\nAlso embeds the non-archived mined ideas, so this one call answers both\n\"what is shipping\" and \"what could we ship\".\n\n`task_scope` is resolved from the key's own credential, not from a browser\nsession - a key narrowed away from tasks sees the calendar without the\nreview tasks attached to it.","operationId":"get_content_calendar_content_calendar_get","parameters":[{"name":"date_from","in":"query","required":true,"schema":{"type":"string","format":"date-time","description":"Window start, inclusive.","title":"Date From"},"description":"Window start, inclusive."},{"name":"date_to","in":"query","required":true,"schema":{"type":"string","format":"date-time","description":"Window end, inclusive.","title":"Date To"},"description":"Window end, inclusive."},{"name":"types","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated lanes to include. Omit for all five. Same vocabulary as the `content_type` path parameter.","title":"Types"},"description":"Comma-separated lanes to include. Omit for all five. Same vocabulary as the `content_type` path parameter."},{"name":"include_unscheduled","in":"query","required":false,"schema":{"type":"boolean","description":"Include pieces with no planned date, capped per lane.","default":true,"title":"Include Unscheduled"},"description":"Include pieces with no planned date, capped per lane."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/content/calendar/ideas/corpus-stats":{"get":{"tags":["Content"],"summary":"Get Idea Corpus Stats","description":"How many conversations each mining lookback tier covers. FREE.\n\nCall this BEFORE `/mine-signals`: the mining cost scales with the corpus,\nand this is the only way to know how big 30, 60 or 90 days actually is for\nthis org before paying for it.","operationId":"get_idea_corpus_stats_content_calendar_ideas_corpus_stats_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/content/calendar/mine-signals/status":{"get":{"tags":["Content"],"summary":"Get Content Signal Mining Status","description":"Progress of the org's signal-mining run. FREE - the poll target for `/mine-signals`.","operationId":"get_content_signal_mining_status_content_calendar_mine_signals_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/content/calendar/ideas":{"get":{"tags":["Content"],"summary":"List Content Ideas","description":"The content idea pool mined from the org's own conversations. FREE.\n\nEach idea's evidence is at `GET /content/calendar/ideas/{idea_id}/evidence`;\n`POST .../create-content` turns one into a draft.","operationId":"list_content_ideas_content_calendar_ideas_get","parameters":[{"name":"archived","in":"query","required":false,"schema":{"type":"boolean","description":"List archived ideas instead of the active pool.","default":false,"title":"Archived"},"description":"List archived ideas instead of the active pool."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/content/calendar/approvals":{"get":{"tags":["Content"],"summary":"List Content Approval Shares","description":"The approval links shared for review, with each one's decision. FREE.","operationId":"list_content_approval_shares_content_calendar_approvals_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"post":{"tags":["Content"],"summary":"Create Content Approval Share","description":"Mint a client-approval link for a piece. FREE.\n\nThe link is a BEARER URL: whoever holds it can approve or reject the piece\nwith no graph8 login. That is what it is for - it goes to a client - but it\nmeans `expires_in_days` is the only thing bounding it, so send a short one\nrather than taking the fourteen-day default by accident.","operationId":"create_content_approval_share_content_calendar_approvals_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateApprovalShareRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/content/calendar/mine-signals":{"post":{"tags":["Content"],"summary":"Mine Content Signals","description":"Mine meeting transcripts and inbox threads for content ideas. SPENDS CREDIT.\n\nThe cost scales with `lookback_days` and the corpus it selects - check\n`/ideas/corpus-stats` first, which is free.\n\nAsynchronous: it returns once the work is dispatched. `include_archived`\nTRUE (the app's default) lets a previously dismissed theme resurface.","operationId":"mine_content_signals_content_calendar_mine_signals_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MineSignalsRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/content/calendar/repurpose/linkedin-post":{"post":{"tags":["Content"],"summary":"Repurpose Content To Linkedin Post","description":"Derive a LinkedIn post DRAFT from an existing piece. SPENDS CREDIT.\n\nA draft: nothing is posted. It lands in the `linkedin_post` lane and a\nreview task is raised against it. Publishing is\n`POST /social/posts/{id}/publish`.","operationId":"repurpose_content_to_linkedin_post_content_calendar_repurpose_linkedin_post_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RepurposeSourceRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/content/calendar/repurpose/ad":{"post":{"tags":["Content"],"summary":"Repurpose Content To Ad","description":"Derive an ad creative from an existing piece. SPENDS CREDIT.\n\n`ads:create`, matching the app - it produces the same object\n`POST /ad-creatives` does, so it carries the same grant rather than riding\nalong on a calendar permission.","operationId":"repurpose_content_to_ad_content_calendar_repurpose_ad_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RepurposeAdRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/content/calendar/ideas/{idea_id}":{"patch":{"tags":["Content"],"summary":"Patch Content Idea","description":"Bookmark, rate or date a mined idea. FREE.\n\nPARTIAL: an ABSENT field is untouched, a field sent as NULL is CLEARED.\nThose are different instructions and only the second one erases - which is\nwhy the proxy forwards `exclude_unset` rather than a full dump.","operationId":"patch_content_idea_content_calendar_ideas__idea_id__patch","parameters":[{"name":"idea_id","in":"path","required":true,"schema":{"type":"string","description":"Mined idea id.","title":"Idea Id"},"description":"Mined idea id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PatchIdeaRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/content/calendar/ideas/{idea_id}/evidence":{"get":{"tags":["Content"],"summary":"Get Content Idea Evidence","description":"Every conversation the idea was mined from. FREE.\n\nThe provenance trail - this is how a human checks that a mined idea is\nreal before spending a generation on it.","operationId":"get_content_idea_evidence_content_calendar_ideas__idea_id__evidence_get","parameters":[{"name":"idea_id","in":"path","required":true,"schema":{"type":"string","description":"Mined idea id.","title":"Idea Id"},"description":"Mined idea id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/content/calendar/ideas/{idea_id}/create-content":{"post":{"tags":["Content"],"summary":"Create Content From Idea","description":"Turn a mined idea into a DRAFT. SPENDS CREDIT, immediately and inline.\n\nNot queued - the generation runs during this call. `format` decides which\ngenerator runs and therefore what it costs; a landing page is the\nexpensive one.","operationId":"create_content_from_idea_content_calendar_ideas__idea_id__create_content_post","parameters":[{"name":"idea_id","in":"path","required":true,"schema":{"type":"string","description":"Mined idea id.","title":"Idea Id"},"description":"Mined idea id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateFromIdeaRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/content/calendar/{content_type}/{content_id}/schedule":{"patch":{"tags":["Content"],"summary":"Schedule Content Piece","description":"Plan a piece's date and owner - or ARM it to publish itself.\n\n`arm: false` (the default) records a date for a human to act on and\nchanges nothing outward-facing.\n\n`arm: true` IS THE OUTWARD-FACING ONE: the publish sweep will send or\ndeploy the piece at `planned_publish_at`, to real people, with no further\nconfirmation. The app requires `campaigns:launch` for that branch\nspecifically, and the principal this proxy hands it is resolved from the\nvalidated key so that check answers correctly rather than silently.\n\n`linkedin_post` REFUSES a date here - LinkedIn schedules belong to\n`POST /social/posts/{id}/schedule`. Owner assignment on a LinkedIn post is\nstill accepted.\n\nSpends nothing.","operationId":"schedule_content_piece_content_calendar__content_type___content_id__schedule_patch","parameters":[{"name":"content_type","in":"path","required":true,"schema":{"enum":["newsletter_issue","landing_page","seo_page","linkedin_post","ad_creative"],"type":"string","description":"Which content lane the piece lives in.","title":"Content Type"},"description":"Which content lane the piece lives in."},{"name":"content_id","in":"path","required":true,"schema":{"type":"string","description":"Id of the piece within that lane.","title":"Content Id"},"description":"Id of the piece within that lane."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ScheduleRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/content/calendar/{content_type}/{content_id}/retry-publish":{"post":{"tags":["Content"],"summary":"Retry Content Publish","description":"Re-arm a failed scheduled publish. IT WILL GO OUT ON THE NEXT SWEEP.\n\nMoves the entry from `failed` back to `scheduled`, which means the same\npiece is published to real people the next time the sweep runs. Same\nlaunch permission and the same tier as arming it in the first place -\n\"retry\" is not a smaller act than \"publish\", it is the same one.\n\nSpends nothing.","operationId":"retry_content_publish_content_calendar__content_type___content_id__retry_publish_post","parameters":[{"name":"content_type","in":"path","required":true,"schema":{"enum":["newsletter_issue","landing_page","seo_page","linkedin_post","ad_creative"],"type":"string","description":"Which content lane the piece lives in.","title":"Content Type"},"description":"Which content lane the piece lives in."},{"name":"content_id","in":"path","required":true,"schema":{"type":"string","description":"Id of the piece within that lane.","title":"Content Id"},"description":"Id of the piece within that lane."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/content/types":{"get":{"tags":["Content"],"summary":"List Content Types","description":"Every content type with its per-status counts. FREE.\n\nThe SOURCE of the `content_type` and `content_status` values the page\nroutes filter and write on.","operationId":"list_content_types_content_types_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/content/website-templates":{"get":{"tags":["Content"],"summary":"List Website Templates","description":"Owned pages reusable as website templates. FREE.\n\nA filtered view of the inventory, not a separate store: every row here is\nalso a content page.","operationId":"list_website_templates_content_website_templates_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":24,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/content/pages/import-sitemap":{"post":{"tags":["Content"],"summary":"Import Content Pages From Sitemap","description":"Bulk-add pages from a sitemap URL. FREE - no provider is called.\n\nIt fetches the sitemap server-side, so it must be publicly reachable. The\ntwo filters are substring matches over each discovered URL; without them a\nlarge sitemap inserts every page it lists.","operationId":"import_content_pages_from_sitemap_content_pages_import_sitemap_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ImportSitemapRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/content/pages/backfill":{"post":{"tags":["Content"],"summary":"Backfill Content Pages","description":"Create inventory rows from website scrapes the org already has. FREE.\n\nReads `cb_intelligence_data` - no site is fetched and no provider is\ncalled. IDEMPOTENT: a page that already exists is skipped rather than\nduplicated.","operationId":"backfill_content_pages_content_pages_backfill_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/content/pages/backfill/status/{task_id}":{"get":{"tags":["Content"],"summary":"Get Content Backfill Status","description":"Progress of a background content backfill. FREE - the poll target.","operationId":"get_content_backfill_status_content_pages_backfill_status__task_id__get","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Task id returned by `POST /content/pages/backfill`.","title":"Task Id"},"description":"Task id returned by `POST /content/pages/backfill`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/content/pages/enrich-seo-bulk":{"post":{"tags":["Content"],"summary":"Enrich Content Pages Bulk","description":"Buy SEO data for many pages at once. SPENDS PROVIDER CREDIT, per page.\n\n`limit` is THE CEILING ON THE SPEND, not a page size - omit `page_ids` and\nthis enriches the next `limit` un-enriched pages and bills for each of\nthem. Send it deliberately.","operationId":"enrich_content_pages_bulk_content_pages_enrich_seo_bulk_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EnrichSeoBulkRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/content/pages":{"get":{"tags":["Content"],"summary":"List Content Pages","description":"The content inventory. FREE.\n\nBoth the org's OWN pages and competitor pages it tracks - `is_owned` is\nthe filter that separates them, and omitting it returns both.","operationId":"list_content_pages_content_pages_get","parameters":[{"name":"domain","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only pages on this domain.","title":"Domain"},"description":"Only pages on this domain."},{"name":"is_owned","in":"query","required":false,"schema":{"anyOf":[{"type":"boolean"},{"type":"null"}],"description":"True for the org's own pages, false for tracked competitors'.","title":"Is Owned"},"description":"True for the org's own pages, false for tracked competitors'."},{"name":"crawl_status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Crawl Status"}},{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source"}},{"name":"content_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"From `GET /content/types`.","title":"Content Type"},"description":"From `GET /content/types`."},{"name":"content_status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Content Status"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"post":{"tags":["Content"],"summary":"Create Content Page","description":"Add one page to the inventory. FREE.\n\n`is_owned` defaults TRUE - this is the org's own page. Set it false to\ntrack a competitor's, which changes what the analytics surfaces count it\ntowards.","operationId":"create_content_page_content_pages_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreatePageRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/content/pages/{page_id}":{"get":{"tags":["Content"],"summary":"Get Content Page","description":"One page, including its stored raw HTML. FREE.","operationId":"get_content_page_content_pages__page_id__get","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","description":"Content page id.","title":"Page Id"},"description":"Content page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Content"],"summary":"Update Content Page","description":"Edit a page's metadata or body. FREE.","operationId":"update_content_page_content_pages__page_id__patch","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","description":"Content page id.","title":"Page Id"},"description":"Content page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdatePageRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Content"],"summary":"Delete Content Page","description":"Remove a page from the inventory.\n\nSpends nothing.","operationId":"delete_content_page_content_pages__page_id__delete","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","description":"Content page id.","title":"Page Id"},"description":"Content page id."},{"name":"force","in":"query","required":false,"schema":{"type":"boolean","description":"Delete even when the page is referenced by grid rows or calendar entries. Without it, a referenced page is refused rather than silently orphaning them.","default":false,"title":"Force"},"description":"Delete even when the page is referenced by grid rows or calendar entries. Without it, a referenced page is refused rather than silently orphaning them."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/content/pages/{page_id}/enrich-seo":{"post":{"tags":["Content"],"summary":"Enrich Content Page","description":"Buy SEO data for ONE page. SPENDS PROVIDER CREDIT.\n\nThe bounded version of the bulk route - one page, one charge.","operationId":"enrich_content_page_content_pages__page_id__enrich_seo_post","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","description":"Content page id.","title":"Page Id"},"description":"Content page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/content/grids":{"get":{"tags":["Content"],"summary":"List Content Grids","description":"The org's content grids. FREE.","operationId":"list_content_grids_content_grids_get","parameters":[{"name":"grid_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter to one grid type.","title":"Grid Type"},"description":"Filter to one grid type."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"post":{"tags":["Content"],"summary":"Create Content Grid","description":"Create a grid - a batch of content jobs. FREE.\n\nCreating the grid costs nothing; the jobs inside it cost when they RUN.","operationId":"create_content_grid_content_grids_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateGridRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/content/grids/{grid_id}":{"get":{"tags":["Content"],"summary":"Get Content Grid","description":"One grid with all its rows and columns. FREE.","operationId":"get_content_grid_content_grids__grid_id__get","parameters":[{"name":"grid_id","in":"path","required":true,"schema":{"type":"string","description":"Content grid id.","title":"Grid Id"},"description":"Content grid id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Content"],"summary":"Delete Content Grid","description":"Delete a grid AND every row in it. The pages the rows referenced stay.\n\nSpends nothing.","operationId":"delete_content_grid_content_grids__grid_id__delete","parameters":[{"name":"grid_id","in":"path","required":true,"schema":{"type":"string","description":"Content grid id.","title":"Grid Id"},"description":"Content grid id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/content/grids/{grid_id}/rows":{"post":{"tags":["Content"],"summary":"Add Content Grid Row","description":"Add one job to a grid. FREE - queuing it is not running it.","operationId":"add_content_grid_row_content_grids__grid_id__rows_post","parameters":[{"name":"grid_id","in":"path","required":true,"schema":{"type":"string","description":"Content grid id.","title":"Grid Id"},"description":"Content grid id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AddRowRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/content/grids/{grid_id}/rows/{row_id}":{"delete":{"tags":["Content"],"summary":"Delete Content Grid Row","description":"Remove one job from a grid.\n\nSpends nothing.","operationId":"delete_content_grid_row_content_grids__grid_id__rows__row_id__delete","parameters":[{"name":"grid_id","in":"path","required":true,"schema":{"type":"string","description":"Content grid id.","title":"Grid Id"},"description":"Content grid id."},{"name":"row_id","in":"path","required":true,"schema":{"type":"string","description":"Row id within the grid.","title":"Row Id"},"description":"Row id within the grid."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/image-library":{"get":{"tags":["Image Library"],"summary":"List Library Images","description":"The org's image library. FREE.\n\nThe SOURCE of the `library_image_id` that `POST /ad-creatives` and\n`POST /ad-creatives/{id}/set-image` accept.","operationId":"list_library_images_image_library_get","parameters":[{"name":"category","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"From `GET /image-library/categories`.","title":"Category"},"description":"From `GET /image-library/categories`."},{"name":"campaign_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id"}},{"name":"source_url","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only images pulled from this page.","title":"Source Url"},"description":"Only images pulled from this page."},{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"How the image got here - extract, upload, ai.","title":"Source"},"description":"How the image got here - extract, upload, ai."},{"name":"include_archived","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Include Archived"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/image-library/categories":{"get":{"tags":["Image Library"],"summary":"List Library Image Categories","description":"Image counts by category. FREE - the vocabulary the filters accept.","operationId":"list_library_image_categories_image_library_categories_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/image-library/counts":{"get":{"tags":["Image Library"],"summary":"Get Library Image Counts","description":"Library-wide totals: `total`, `by_category`, `by_source` (web, generated, uploaded) and the `logos`. FREE.\n\nNot limited to a page, and with the same visibility as the list (drafts and thumbs-down hidden). `logos` carries the\nfew fields needed to tell the brand's own logos from external ones.","operationId":"get_library_image_counts_image_library_counts_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/image-library/{image_id}/raw":{"get":{"tags":["Image Library"],"summary":"Get Library Image Raw","description":"The bytes of a legacy library image whose address is a `data:` URI. FREE.\n\nMost images are hosted and have an ordinary `image_url`; this is for the older rows that carry the bytes inline and\nare listed with a signed `raw` address instead. The KEY authorises the read: the organisation is the key's own and the\napp's expiring signature is minted here for exactly (organisation, image), so an image of another organisation is a\n404. 413 for an image over the size cap, 415 for data that is not an image, 503 when signing is not configured.","operationId":"get_library_image_raw_image_library__image_id__raw_get","parameters":[{"name":"image_id","in":"path","required":true,"schema":{"type":"string","description":"Image id (UUID).","title":"Image Id"},"description":"Image id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"The image bytes","content":{"image/*":{"schema":{"type":"string","format":"binary"}}}},"307":{"description":"The image now lives on one of graph8's own image hosts; follow the redirect"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-response-format":"binary","x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/image-library/extract":{"post":{"tags":["Image Library"],"summary":"Extract Images From Website","description":"Pull every image off one page into the library. FREE - no model runs.\n\nIt fetches the URL server-side, so the page must be publicly reachable.\n`min_width` / `min_height` are what keep the icons and tracking pixels\nout; lowering them floods the library rather than enriching it.\n\nAsynchronous - it returns once the extraction is dispatched.","operationId":"extract_images_from_website_image_library_extract_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ExtractImagesRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/image-library/extract-all-pages":{"post":{"tags":["Image Library"],"summary":"Extract Images From All Pages","description":"Run the extraction over EVERY stored content page. FREE, but broad.\n\nNo credit is spent and no site is re-fetched - it reads the HTML already\nstored against each content page. The cost is in the library: on a large\ninventory this can add a great many images at once, and there is no\nper-page filter. `POST /extract` is the bounded version.","operationId":"extract_images_from_all_pages_image_library_extract_all_pages_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/image-library/generated/{image_id}/commit":{"post":{"tags":["Image Library"],"summary":"Commit Generated Image","description":"Promote an AI DRAFT into a durable library asset. FREE.\n\nA draft lives on a 24-hour TTL and its storage object is swept. Commit it\nbefore referencing it from a page you intend to publish, or the page ends\nup pointing at an object that has been collected.","operationId":"commit_generated_image_image_library_generated__image_id__commit_post","parameters":[{"name":"image_id","in":"path","required":true,"schema":{"type":"string","description":"Image id (UUID).","title":"Image Id"},"description":"Image id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/image-library/generated/{image_id}":{"delete":{"tags":["Image Library"],"summary":"Discard Generated Image","description":"Throw an uncommitted AI draft away, and its storage object with it.\n\nOnly DRAFTS. A committed asset is `DELETE /image-library/{image_id}`,\nwhich is gated differently on purpose.\n\nSpends nothing.","operationId":"discard_generated_image_image_library_generated__image_id__delete","parameters":[{"name":"image_id","in":"path","required":true,"schema":{"type":"string","description":"Image id (UUID).","title":"Image Id"},"description":"Image id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/image-library/{image_id}":{"delete":{"tags":["Image Library"],"summary":"Delete Library Image","description":"Delete a durable image from the library.\n\nANY published page or live ad still pointing at it breaks. `campaigns:delete`,\nwhich is the app's own gate and a deliberately narrower one than the rest\nof this router carries.\n\nSpends nothing.","operationId":"delete_library_image_image_library__image_id__delete","parameters":[{"name":"image_id","in":"path","required":true,"schema":{"type":"string","description":"Image id (UUID).","title":"Image Id"},"description":"Image id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/image-library/{image_id}/feedback":{"patch":{"tags":["Image Library"],"summary":"Set Library Image Feedback","description":"Thumbs up or down on an image. FREE.\n\n`feedback: null` CLEARS the existing rating rather than leaving it - there\nis no separate delete.","operationId":"set_library_image_feedback_image_library__image_id__feedback_patch","parameters":[{"name":"image_id","in":"path","required":true,"schema":{"type":"string","description":"Image id (UUID).","title":"Image Id"},"description":"Image id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ImageFeedbackRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/image-library/{image_id}/category":{"patch":{"tags":["Image Library"],"summary":"Set Library Image Category","description":"Recategorise an image. FREE. Categories come from `/categories`.","operationId":"set_library_image_category_image_library__image_id__category_patch","parameters":[{"name":"image_id","in":"path","required":true,"schema":{"type":"string","description":"Image id (UUID).","title":"Image Id"},"description":"Image id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ImageCategoryRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/image-library/{image_id}/alt-text":{"patch":{"tags":["Image Library"],"summary":"Set Library Image Alt Text","description":"Set the alt text. FREE.\n\nIt is ALSO the library display name, so this is not only an accessibility\nfield - changing it renames the image everywhere Studio shows it.","operationId":"set_library_image_alt_text_image_library__image_id__alt_text_patch","parameters":[{"name":"image_id","in":"path","required":true,"schema":{"type":"string","description":"Image id (UUID).","title":"Image Id"},"description":"Image id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ImageAltTextRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/image-library/extract/status/{task_id}":{"get":{"tags":["Image Library"],"summary":"Get Image Extraction Status","description":"Progress of a background image extraction. FREE - the poll target.","operationId":"get_image_extraction_status_image_library_extract_status__task_id__get","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Task id returned by `POST /image-library/extract`.","title":"Task Id"},"description":"Task id returned by `POST /image-library/extract`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/image-library/{image_id}/tags":{"patch":{"tags":["Image Library"],"summary":"Set Library Image Tags","description":"REPLACE an image's tags (e.g. `main_logo`, `dark_mode`). FREE.\n\nThe list you send is the whole new set; send `[]` to clear them.\nGeneration reads these tags to pick the right logo variant.","operationId":"set_library_image_tags_image_library__image_id__tags_patch","parameters":[{"name":"image_id","in":"path","required":true,"schema":{"type":"string","description":"Image id (UUID).","title":"Image Id"},"description":"Image id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ImageTagsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/image-library/duplicates/scan":{"post":{"tags":["Image Library"],"summary":"Scan Library Duplicates","description":"Find groups of duplicate images in the library. FREE, and changes nothing.\n\nThe input to `POST /image-library/duplicates/merge`: each group names the\nimages that are the same picture.","operationId":"scan_library_duplicates_image_library_duplicates_scan_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/image-library/duplicates/merge":{"post":{"tags":["Image Library"],"summary":"Merge Library Duplicates","description":"Merge duplicates into one keeper. The duplicates are REMOVED.\n\nReferences to a duplicate are re-pointed at the keeper first, so nothing\nthat used one breaks. Gated like a delete (`campaigns:delete`), because\nit is one - the app's own `_require_library_management`.\n\nSpends nothing.","operationId":"merge_library_duplicates_image_library_duplicates_merge_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ImageMergeDuplicatesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/research-reports/generate":{"post":{"tags":["Research"],"summary":"Generate Research Report","description":"Generate ONE of the six reports. SPENDS CREDIT - heavily.\n\nA long multi-pass run against the market, the customer's own site and its\ncompetitors. This is the most expensive single operation in Studio.\n\nAsynchronous: it returns once the run is dispatched. Poll\n`GET /research-reports/workflow?website_url=...` for progress.","operationId":"generate_research_report_research_reports_generate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/GenerateReportRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/research-reports/generate-all":{"post":{"tags":["Research"],"summary":"Generate All Research Reports","description":"Generate all SIX reports for a website. SPENDS CREDIT, six times over.\n\nThe single largest spend this API can trigger. `/stop-all` cancels a run\nin flight, but whatever has already been generated has already been paid\nfor.","operationId":"generate_all_research_reports_research_reports_generate_all_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/GenerateAllReportsRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/research-reports/scaffold":{"post":{"tags":["Research"],"summary":"Scaffold Research Reports","description":"Create the six report PLACEHOLDERS. FREE - nothing is generated.\n\nEmpty rows you can then fill by editing, or by generating into them one at\na time. The cheap way to see the six report types before committing to a\nrun.","operationId":"scaffold_research_reports_research_reports_scaffold_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/research-reports/stop-all":{"post":{"tags":["Research"],"summary":"Stop All Research","description":"Stop every running report for a website. FREE.\n\nIt cancels what has not started. Anything already generated stays, and\nanything already generated has already been charged for.","operationId":"stop_all_research_research_reports_stop_all_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/GenerateAllReportsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/research-reports/workflow":{"get":{"tags":["Research"],"summary":"Get Research Workflow Status","description":"How the six-report workflow is going for one website. FREE.\n\nThe poll target for `/generate` and `/generate-all`, and the read to make\nbefore `/workflow/resume` - it says which reports are actually incomplete,\nand therefore what resuming would cost.","operationId":"get_research_workflow_status_research_reports_workflow_get","parameters":[{"name":"website_url","in":"query","required":true,"schema":{"type":"string","description":"The website the workflow is scoped to.","title":"Website Url"},"description":"The website the workflow is scoped to."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/research-reports/workflow/reset":{"post":{"tags":["Research"],"summary":"Reset Research Workflow","description":"Reset the workflow to start fresh. NOT REVERSIBLE.\n\nIt discards the workflow's progress. Nothing is spent by resetting - but\neverything that was generated has to be generated again, so the real cost\nof this call is the run that follows it.\n\nSpends nothing.","operationId":"reset_research_workflow_research_reports_workflow_reset_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/GenerateAllReportsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/research-reports/workflow/resume":{"post":{"tags":["Research"],"summary":"Resume Research Workflow","description":"Restart a stuck workflow. SPENDS CREDIT - it generates what is missing.\n\n\"Resume\" understates it: every incomplete report is generated, which can\nbe all six. Read `GET /research-reports/workflow` first to see how many\nthat is. Its path carries no `/generate`, so the tier heuristic called\nthis an ordinary write; it is corrected with an explicit rule.","operationId":"resume_research_workflow_research_reports_workflow_resume_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/research-reports/retry":{"post":{"tags":["Research"],"summary":"Retry Research Report","description":"Re-run ONE failed report. SPENDS CREDIT - it is a full generation of that report.\n\nThe existing report row is reused, so a worker still writing to it does not\nlose its target. Poll `GET /research-reports/workflow?website_url=...`.","operationId":"retry_research_report_research_reports_retry_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RetryResearchReportRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/research-reports/by-number/{report_number}":{"get":{"tags":["Research"],"summary":"Get Research Report By Number","description":"One report by its POSITION in the six, for a website. FREE.\n\n`/by-number/` rather than the app's singular `/report/{n}`: a path that\ndiffers from `/research-reports/{id}` only by a letter is the trap this\nprogramme has already paid for once.","operationId":"get_research_report_by_number_research_reports_by_number__report_number__get","parameters":[{"name":"report_number","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Report number, 1-6.","title":"Report Number"},"description":"Report number, 1-6."},{"name":"website_url","in":"query","required":true,"schema":{"type":"string","description":"The website the workflow is scoped to.","title":"Website Url"},"description":"The website the workflow is scoped to."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/research-reports/{report_id}":{"get":{"tags":["Research"],"summary":"Get Research Report","description":"One research report with its full markdown. FREE.\n\nDeclared AFTER every literal on this router (`/workflow`, `/by-number/...`)\nso it cannot swallow them.","operationId":"get_research_report_research_reports__report_id__get","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","description":"Research report id.","title":"Report Id"},"description":"Research report id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Research"],"summary":"Delete Research Report","description":"Delete a report. Regenerating it costs a full run, so this is expensive\nto undo even though the deletion itself is free.","operationId":"delete_research_report_research_reports__report_id__delete","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","description":"Research report id.","title":"Report Id"},"description":"Research report id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"},"patch":{"tags":["GTM Context"],"summary":"Update Research Report","description":"Update a Research report's markdown content and/or status.\n\nRead-side counterpart already exists (``GET /research-reports``); this\ncloses the \"read but can't update\" gap for the Research bucket. On a content\nchange it creates a ``DocumentVersion`` snapshot AND re-indexes the report to\nthe RAG knowledge base — identical to the internal Studio editor, so search\nnever goes stale relative to an API-driven edit.\n\nPartial update: send ``markdown_content``, ``status``, or both. Returns 400\nif neither is provided, 404 if the report does not exist in this org. A\nreport already 'completed'/'approved' can only move between those two states.","operationId":"update_research_report_research_reports__report_id__patch","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","description":"Research report ID (UUID)","title":"Report Id"},"description":"Research report ID (UUID)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateResearchReportRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/research-reports/{report_id}/approve":{"post":{"tags":["Research"],"summary":"Approve Research Report","description":"Approve a report and INDEX IT INTO THE KNOWLEDGE BASE. FREE.\n\nApproving is what makes the report reachable from retrieval - every\ncampaign, sequence and copilot answer grounded on knowledge can quote it\nafterwards. That is a wider blast radius than \"set a status\", which is why\nit has its own route rather than being a field on the PATCH.","operationId":"approve_research_report_research_reports__report_id__approve_post","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","description":"Research report id.","title":"Report Id"},"description":"Research report id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/research-reports/{report_id}/unapprove":{"post":{"tags":["Research"],"summary":"Unapprove Research Report","description":"Remove a report from the knowledge index. FREE. The report survives.","operationId":"unapprove_research_report_research_reports__report_id__unapprove_post","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","description":"Research report id.","title":"Report Id"},"description":"Research report id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/global-context/documents/{doc_id}/revise":{"post":{"tags":["GTM Context"],"summary":"Revise Global Document","description":"Queue an AI rewrite of one global-context document. THIS SPENDS CREDITS (a model job).\n\nThe result lands as a draft; the live text is untouched until you `draft/accept`. A follow-up instruction builds on a\npending draft. 402 when the organisation cannot pay, 400 when the document has no content yet.","operationId":"revise_global_document_global_context_documents__doc_id__revise_post","parameters":[{"name":"doc_id","in":"path","required":true,"schema":{"type":"string","description":"The document id (UUID) or its type, e.g. `brand_brief`.","title":"Doc Id"},"description":"The document id (UUID) or its type, e.g. `brand_brief`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DocumentRevisionRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/global-context/documents/{doc_id}/draft/accept":{"post":{"tags":["GTM Context"],"summary":"Accept Global Document Draft","description":"Apply the draft (all sections, or the `section_keys` you name) as a new live version. 409 when there is no draft.","operationId":"accept_global_document_draft_global_context_documents__doc_id__draft_accept_post","parameters":[{"name":"doc_id","in":"path","required":true,"schema":{"type":"string","description":"The document id (UUID) or its type, e.g. `brand_brief`.","title":"Doc Id"},"description":"The document id (UUID) or its type, e.g. `brand_brief`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DocumentDraftAcceptRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/global-context/documents/{doc_id}/draft/discard":{"post":{"tags":["GTM Context"],"summary":"Discard Global Document Draft","description":"Drop the draft. The live document is not touched.","operationId":"discard_global_document_draft_global_context_documents__doc_id__draft_discard_post","parameters":[{"name":"doc_id","in":"path","required":true,"schema":{"type":"string","description":"The document id (UUID) or its type, e.g. `brand_brief`.","title":"Doc Id"},"description":"The document id (UUID) or its type, e.g. `brand_brief`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/research-reports/{report_id}/revise":{"post":{"tags":["GTM Context"],"summary":"Revise Research Report","description":"Queue an AI rewrite of one research report. THIS SPENDS CREDITS (a model job).\n\nThe result lands as a draft; the live report is untouched until you `draft/accept`. 402 when the organisation cannot\npay, 400 when the report has no content yet.","operationId":"revise_research_report_research_reports__report_id__revise_post","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","description":"The research report id (UUID).","title":"Report Id"},"description":"The research report id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ReportRevisionRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/research-reports/{report_id}/draft/accept":{"post":{"tags":["GTM Context"],"summary":"Accept Research Report Draft","description":"Apply the draft (all sections, or the `section_keys` you name) as a NEW VERSION of the report. 409 when none.","operationId":"accept_research_report_draft_research_reports__report_id__draft_accept_post","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","description":"The research report id (UUID).","title":"Report Id"},"description":"The research report id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ReportDraftAcceptRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/research-reports/{report_id}/draft/discard":{"post":{"tags":["GTM Context"],"summary":"Discard Research Report Draft","description":"Drop the draft. The live report is not touched.","operationId":"discard_research_report_draft_research_reports__report_id__draft_discard_post","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","description":"The research report id (UUID).","title":"Report Id"},"description":"The research report id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/campaigns/generation-options":{"get":{"tags":["Campaigns"],"summary":"Get Campaign Generation Options","description":"The supported generation contract: goals, channels, execution targets. FREE.\n\nThe SOURCE of the vocabularies `/generate-ideas` and `/generate-ideas-async`\naccept. Read it before generating, because an unrecognised channel is\nsilently ignored rather than rejected.","operationId":"get_campaign_generation_options_campaigns_generation_options_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/campaigns/picker":{"get":{"tags":["Campaigns"],"summary":"List Campaigns For Picker","description":"Every campaign in the org, id and name only. FREE.\n\nUNSCOPED BY DESIGN, and that is worth knowing: it deliberately ignores the\nown/team/all campaign scope so a picker can offer every campaign a call\ncould be logged against. It returns identifiers, not campaign content - use\n`GET /campaigns` for the scoped, full list.","operationId":"list_campaigns_for_picker_campaigns_picker_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/campaigns/audience-lists/options":{"get":{"tags":["Campaigns"],"summary":"List Campaign Audience List Options","description":"Contact lists a campaign can be built on. FREE.\n\nScoped to what the CREDENTIAL can see: a key narrowed away from lists gets\nthe lists it is entitled to, not all of them.","operationId":"list_campaign_audience_list_options_campaigns_audience_lists_options_get","parameters":[{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Substring match on the list name.","title":"Search"},"description":"Substring match on the list name."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/campaigns/document-manifest/preview":{"post":{"tags":["Campaigns"],"summary":"Preview Campaign Document Manifest","description":"Which documents a campaign with these channels would generate. FREE.\n\nA dry run of the generation contract: nothing is created and no model\nruns. The same answer `POST /campaigns` acts on.","operationId":"preview_campaign_document_manifest_campaigns_document_manifest_preview_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CampaignDocumentManifestRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/campaigns/audience-profile/preview":{"post":{"tags":["Campaigns"],"summary":"Preview Campaign Audience Profile","description":"Profile an audience list before building a campaign on it. FREE.\n\nAggregates the list's titles, seniority and industries so the campaign\ncan be aimed at who is actually on it. Nothing is created.","operationId":"preview_campaign_audience_profile_campaigns_audience_profile_preview_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AudienceProfilePreviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/campaigns/suggest":{"post":{"tags":["Campaigns"],"summary":"Suggest Campaign Concepts","description":"Rank the top 15 campaign CONCEPTS from the playbook library for a goal.\n\nSemantic search over the concept library plus rule-based scoring (fit,\nasset readiness, goal, channel feasibility). No generative model runs and\nnothing is created - `POST /campaigns/generate-ideas` is the generative,\ncredit-spending counterpart. `organization_id` in the body is ignored.\n\nSpends nothing.","operationId":"suggest_campaign_concepts_campaigns_suggest_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuggestCampaignsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/campaigns/ideas/status/{task_id}":{"get":{"tags":["Campaigns"],"summary":"Get Campaign Ideas Task Status","description":"Progress of a background idea-generation run. FREE - the poll target.","operationId":"get_campaign_ideas_task_status_campaigns_ideas_status__task_id__get","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Task id returned by `POST /campaigns/generate-ideas-async`.","title":"Task Id"},"description":"Task id returned by `POST /campaigns/generate-ideas-async`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/campaigns/recommend-personas":{"post":{"tags":["Campaigns"],"summary":"Recommend Campaign Personas","description":"Recommend target personas and a strategy. SPENDS CREDIT.\n\nAn LLM pass over the company's own data. Its path carries no marker, so\nthe tier heuristic called it an ordinary write; it is corrected with an\nexplicit rule.\n\n`organization_id` in the body is IGNORED - the organisation is always the\nAPI key's own. It is accepted because the app's model carries it, and\nrejecting a field Studio itself sends would be a gratuitous 422.","operationId":"recommend_campaign_personas_campaigns_recommend_personas_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonaRecommendationRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/campaigns/generate-ideas":{"post":{"tags":["Campaigns"],"summary":"Generate Campaign Ideas","description":"Generate campaign ideas. SPENDS CREDIT, scaled by `num_ideas`.\n\nSYNCHRONOUS: the generation runs during this call, so a large `num_ideas`\nis a long request. Use `/generate-ideas-async` for anything big.","operationId":"generate_campaign_ideas_campaigns_generate_ideas_post","parameters":[{"name":"num_ideas","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"description":"How many ideas. Scales the spend.","default":5,"title":"Num Ideas"},"description":"How many ideas. Scales the spend."},{"name":"user_direction","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Free-text steer for the generator.","title":"User Direction"},"description":"Free-text steer for the generator."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuggestCampaignsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/campaigns/generate-ideas-async":{"post":{"tags":["Campaigns"],"summary":"Generate Campaign Ideas Async","description":"The same generation, dispatched to the background. SPENDS CREDIT.\n\nReturns a task id immediately. The spend is committed by this call even\nthough the ideas are not here yet - cancelling the poll does not cancel\nthe run.","operationId":"generate_campaign_ideas_async_campaigns_generate_ideas_async_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AsyncGenerateIdeasRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/campaigns/ideas/manual":{"post":{"tags":["Campaigns"],"summary":"Create Manual Campaign Idea","description":"Add an idea by hand, with no generation. FREE.\n\nThe zero-cost way into the idea pool: everything `/generate-ideas` produces\ncan also be written directly here.","operationId":"create_manual_campaign_idea_campaigns_ideas_manual_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"The idea's fields. An OPEN object because the app's handler takes a bare dict and writes the recognised keys - mirroring it as a closed model would silently drop whatever the grid learned to send between two deploys.","title":"Idea"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/campaigns/ideas/{idea_id}":{"patch":{"tags":["Campaigns"],"summary":"Update Campaign Idea","description":"Edit an idea in place. FREE.\n\nThe ownership scope IS the permission gate here, exactly as in the app -\nthere is no separate `campaigns:write` check on this route, so the\nper-record gate is the only thing between a key and another user's idea.\nThat is why it is re-declared rather than assumed.","operationId":"update_campaign_idea_campaigns_ideas__idea_id__patch","parameters":[{"name":"idea_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign idea id.","title":"Idea Id"},"description":"Campaign idea id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Fields to change. Open for the same reason the create body is.","title":"Updates"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Campaigns"],"summary":"Delete Campaign Idea","description":"PERMANENTLY delete an idea. Archiving is the reversible alternative.\n\nTwo gates, matching the app: the per-record ownership scope AND\n`campaigns:delete`. Both are re-declared here because neither runs on a\ndirect call - the first is a decorator dependency, the second a signature\none.\n\nSpends nothing.","operationId":"delete_campaign_idea_campaigns_ideas__idea_id__delete","parameters":[{"name":"idea_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign idea id.","title":"Idea Id"},"description":"Campaign idea id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/campaigns/ideas/{idea_id}/favorite":{"post":{"tags":["Campaigns"],"summary":"Toggle Campaign Idea Favorite","description":"TOGGLE the favourite flag on an idea. FREE.\n\nA toggle, not a setter - the app has no explicit-value form, so a retried\nrequest flips the state back rather than being idempotent. Read the\nreturned value rather than assuming the call set it.","operationId":"toggle_campaign_idea_favorite_campaigns_ideas__idea_id__favorite_post","parameters":[{"name":"idea_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign idea id.","title":"Idea Id"},"description":"Campaign idea id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}":{"delete":{"tags":["Campaigns"],"summary":"Delete Campaign","description":"SOFT-delete a campaign. It stops appearing; its rows are not dropped.\n\nThe contract could create, read, patch and LAUNCH a campaign and never\nremove one. `campaigns:delete` plus the per-record ownership scope, both\nthe app's own gates.\n\nSpends nothing.","operationId":"delete_campaign_campaigns__campaign_id__delete","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id or slug.","title":"Campaign Id"},"description":"Campaign id or slug."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"},"get":{"tags":["GTM Campaigns"],"summary":"Get Campaign","description":"Get details of a specific campaign including generated documents.","operationId":"get_campaign_campaigns__campaign_id__get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["GTM Campaigns"],"summary":"Update Campaign","description":"Update campaign content fields (name, brief, hook, persona, etc.).","operationId":"update_campaign_campaigns__campaign_id__patch","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/developer_api__interfaces__v1__gtm_campaigns_router__CampaignUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/restore":{"post":{"tags":["Campaigns"],"summary":"Restore Campaign","description":"Undo the soft delete from `DELETE /campaigns/{campaign_id}`: the campaign appears again.\n\nThe same two gates as the delete, re-declared (neither runs on a direct call): the per-record ownership scope AND\n`campaigns:delete`, so whoever may archive a campaign may restore it. A campaign that is not archived answers 200\nwith \"Campaign is not archived\" and changes nothing. Fires the `campaign.restored` webhook, as in the app.\n\nSpends nothing.","operationId":"restore_campaign_campaigns__campaign_id__restore_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id or slug.","title":"Campaign Id"},"description":"Campaign id or slug."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/dashboard":{"get":{"tags":["Campaigns"],"summary":"Get Campaign Dashboard","description":"The AI campaign dashboard. A GET THAT CAN SPEND CREDIT.\n\nOn a cache hit it is free and instant. On a MISS - or when the cached copy\nis stale and the campaign's documents have changed - it dispatches a\nbackground job that generates the assessment with a model, and returns\n`is_generating: true`. So the first call for a campaign costs money even\nthough it is a GET.\n\nThat is why it is tiered `billable` rather than `read`: the heuristic's\n`ACTIVE_GET_MARKERS` exist for exactly this shape and none of them matches\n`/dashboard`. Poll every few seconds while `is_generating` is true;\npolling does not re-dispatch.","operationId":"get_campaign_dashboard_campaigns__campaign_id__dashboard_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id or slug.","title":"Campaign Id"},"description":"Campaign id or slug."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/landing-pages":{"get":{"tags":["Campaigns"],"summary":"List Campaign Landing Pages","description":"The landing pages this campaign runs on. FREE.","operationId":"list_campaign_landing_pages_campaigns__campaign_id__landing_pages_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id or slug.","title":"Campaign Id"},"description":"Campaign id or slug."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"post":{"tags":["Campaigns"],"summary":"Link Landing Page To Campaign","description":"Attach an existing landing page to this campaign. FREE.\n\nA link, not a copy: the page is unchanged and can be linked to more than\none campaign. Create the page with `POST /landing-pages` first.","operationId":"link_landing_page_to_campaign_campaigns__campaign_id__landing_pages_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id or slug.","title":"Campaign Id"},"description":"Campaign id or slug."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LinkLandingPageRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/landing-pages/{landing_page_id}":{"delete":{"tags":["Campaigns"],"summary":"Unlink Landing Page From Campaign","description":"Detach a landing page from this campaign. The PAGE IS NOT DELETED.\n\nIt keeps serving at every URL it is published at - unlinking is an\norganisational act, not a takedown. Use\n`POST /landing-pages/{id}/unpublish` for that.\n\nThe app has a SECOND route for this same operation, spelled\n`DELETE /v1/landing-pages/campaigns/{campaign_id}/{landing_page_id}`. Only\nthis spelling is published: two paths for one act is how a caller ends up\nreading one and writing the other.\n\nSpends nothing.","operationId":"unlink_landing_page_from_campaign_campaigns__campaign_id__landing_pages__landing_page_id__delete","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id or slug.","title":"Campaign Id"},"description":"Campaign id or slug."},{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"The landing page to detach.","title":"Landing Page Id"},"description":"The landing page to detach."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/status":{"get":{"tags":["Campaigns"],"summary":"Get Campaign Generation Status","description":"Whether the campaign's documents have finished generating. FREE.\n\nThe poll target after creating a campaign: generation runs in the\nbackground and this reports its progress.","operationId":"get_campaign_generation_status_campaigns__campaign_id__status_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id or slug.","title":"Campaign Id"},"description":"Campaign id or slug."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/files":{"get":{"tags":["Campaigns"],"summary":"List Campaign Generated Files","description":"The generated files of a campaign, by type. FREE.","operationId":"list_campaign_generated_files_campaigns__campaign_id__files_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id or slug.","title":"Campaign Id"},"description":"Campaign id or slug."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/files/{file_type}":{"get":{"tags":["Campaigns"],"summary":"Get Campaign Generated File","description":"One generated file's content. FREE.","operationId":"get_campaign_generated_file_campaigns__campaign_id__files__file_type__get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id or slug.","title":"Campaign Id"},"description":"Campaign id or slug."},{"name":"file_type","in":"path","required":true,"schema":{"type":"string","description":"A file type from `GET /campaigns/{campaign_id}/files`.","title":"File Type"},"description":"A file type from `GET /campaigns/{campaign_id}/files`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/campaigns/ideas/{idea_id}/archive":{"post":{"tags":["Campaigns"],"summary":"Archive Campaign Idea","description":"Archive an idea. FREE.\n\nArchived ideas are not deleted: future idea generation reads them - and\nthe `reason` - to steer away from similar concepts.","operationId":"archive_campaign_idea_campaigns_ideas__idea_id__archive_post","parameters":[{"name":"idea_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign idea id.","title":"Idea Id"},"description":"Campaign idea id."},{"name":"reason","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"description":"Why it was archived.","title":"Reason"},"description":"Why it was archived."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/documents/{document_id}/regenerate":{"post":{"tags":["Campaigns"],"summary":"Regenerate Campaign Document","description":"Rewrite ONE campaign document with AI. SPENDS CREDIT.\n\nThe document is marked `generating` and a background job rewrites it from\nthe campaign's current context; poll `GET /campaigns/{campaign_id}/documents/{document_id}`.\nThe current content is replaced.","operationId":"regenerate_campaign_document_campaigns__campaign_id__documents__document_id__regenerate_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id or slug.","title":"Campaign Id"},"description":"Campaign id or slug."},{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign document id.","title":"Document Id"},"description":"Campaign document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/sequence/steps/{step_id}/generate":{"post":{"tags":["Campaigns"],"summary":"Generate Campaign Step Content","description":"Write the content for ONE sequence step with AI, replacing its placeholder. SPENDS CREDIT.","operationId":"generate_campaign_step_content_campaigns__campaign_id__sequence_steps__step_id__generate_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id or slug.","title":"Campaign Id"},"description":"Campaign id or slug."},{"name":"step_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence step id, from `GET /campaigns/{campaign_id}/sequence`.","title":"Step Id"},"description":"Sequence step id, from `GET /campaigns/{campaign_id}/sequence`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/knowledge/tree":{"get":{"tags":["Knowledge"],"summary":"Browse Knowledge Tree","description":"Browse the knowledge tree one folder at a time. FREE.\n\nThe structural read `GET /knowledge` cannot do: that one returns a flat\nfiltered list, this one walks the hierarchy the brain is actually organised\ninto. Page with `cursor`.","operationId":"browse_knowledge_tree_knowledge_tree_get","parameters":[{"name":"parent","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":512},{"type":"null"}],"description":"Folder to list. Omit for the root.","title":"Parent"},"description":"Folder to list. Omit for the root."},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":1024},{"type":"null"}],"title":"Cursor"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/knowledge/status":{"get":{"tags":["Knowledge"],"summary":"Get Knowledge Status","description":"How complete and how fresh the knowledge brain is. FREE.\n\nCounts by trust tier and freshness, restricted to what this credential's\nrecord scopes can see.","operationId":"get_knowledge_status_knowledge_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/knowledge/authored":{"post":{"tags":["Knowledge"],"summary":"Create Authored Knowledge","description":"Write a knowledge concept by hand. FREE.\n\nGOVERNED, not immediate: the entry lands as a draft in the review queue at\n`GET /knowledge/governance` and does not project into the brain's answers\nuntil it is approved there. Writing here is proposing, not publishing.","operationId":"create_authored_knowledge_knowledge_authored_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AuthoredKnowledgeRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/knowledge/authored/{concept_id}":{"patch":{"tags":["Knowledge"],"summary":"Update Authored Knowledge Draft","description":"Edit a concept that is still a DRAFT. FREE.\n\nOnly while it is unapproved. Once it has been approved, changing it is an\nAMENDMENT - `POST /authored/{id}/amendments` - which is a new governed\nrevision rather than an edit in place.","operationId":"update_authored_knowledge_draft_knowledge_authored__concept_id__patch","parameters":[{"name":"concept_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"Concept id.","title":"Concept Id"},"description":"Concept id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AuthoredKnowledgeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/knowledge/authored/{concept_id}/amendments":{"post":{"tags":["Knowledge"],"summary":"Create Authored Knowledge Amendment","description":"Propose a revision to an APPROVED concept. FREE.\n\nThe approved version keeps answering until the amendment is approved in\nits turn, so proposing one never leaves the brain with a gap.","operationId":"create_authored_knowledge_amendment_knowledge_authored__concept_id__amendments_post","parameters":[{"name":"concept_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"Concept id.","title":"Concept Id"},"description":"Concept id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AuthoredKnowledgeRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/knowledge/authored/{concept_id}/deprecate":{"post":{"tags":["Knowledge"],"summary":"Deprecate Authored Knowledge","description":"Retire a concept so the brain stops answering from it.\n\nThe record and its history survive - this removes it from retrieval, it\ndoes not delete it. `reason` is required and is kept on the record, which\nis the point: a retired concept with no stated reason is indistinguishable\nfrom one retired by mistake. Name `superseded_by` when something replaces\nit.\n\nSpends nothing.","operationId":"deprecate_authored_knowledge_knowledge_authored__concept_id__deprecate_post","parameters":[{"name":"concept_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"Concept id.","title":"Concept Id"},"description":"Concept id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeprecateKnowledgeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/knowledge/{concept_id}/history":{"get":{"tags":["Knowledge"],"summary":"Get Knowledge History","description":"A concept's revision history - every authored version, amendment,\nverification and deprecation, newest first. FREE. Page with `cursor`.","operationId":"get_knowledge_history_knowledge__concept_id__history_get","parameters":[{"name":"concept_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"Concept id.","title":"Concept Id"},"description":"Concept id."},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":1024},{"type":"null"}],"title":"Cursor"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/knowledge/authored/{concept_id}/verify":{"post":{"tags":["Knowledge"],"summary":"Verify Authored Knowledge","description":"Approve or reject a PROPOSED concept. FREE.\n\nApproving makes it answerable - every retrieval grounded on knowledge can\nquote it from this moment - and records `authority` as who vouched for it.\nRejecting keeps it out of the brain.","operationId":"verify_authored_knowledge_knowledge_authored__concept_id__verify_post","parameters":[{"name":"concept_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"Concept id.","title":"Concept Id"},"description":"Concept id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VerifyKnowledgeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/website-editor/connect":{"post":{"tags":["Website Editor"],"summary":"Connect Website Hosting","description":"Connect the org's website hosting account. FREE.\n\nThe credentials are validated against the provider before they are stored,\nso a wrong token is a 400 rather than a broken connection. Replaces any\nexisting connection. The token is WRITE-ONLY - no response carries it.","operationId":"connect_website_hosting_website_editor_connect_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WebsiteEditorConnectRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebsiteEditorConnection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/website-editor/disconnect":{"delete":{"tags":["Website Editor"],"summary":"Disconnect Website Hosting","description":"Remove the hosting connection and its stored credentials. FREE.\n\nPages already synced stay in the content workspace; publishing afterwards\ngoes to the graph8-hosted site instead of the org's own account.","operationId":"disconnect_website_hosting_website_editor_disconnect_delete","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/website-editor/connection":{"get":{"tags":["Website Editor"],"summary":"Get Website Hosting Connection","description":"Whether a hosting account is connected, and its sync status. FREE.","operationId":"get_website_hosting_connection_website_editor_connection_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebsiteEditorConnection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/website-editor/projects":{"get":{"tags":["Website Editor"],"summary":"List Website Hosting Projects","description":"The site projects in the connected hosting account. FREE.\n\nThe valid `project_name` values for `POST /website-editor/sync`. 404 when\nno account is connected.","operationId":"list_website_hosting_projects_website_editor_projects_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/website-editor/sync":{"post":{"tags":["Website Editor"],"summary":"Sync Website Pages","description":"Pull pages from a hosted site project into Studio. FREE.\n\nEach page's HTML is tagged with stable element ids and stored; a page that\nalready exists (matched by URL, then by path) is OVERWRITTEN with the live\nHTML, so unpublished edits to it are replaced. Omit `paths` for every page.","operationId":"sync_website_pages_website_editor_sync_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WebsiteEditorSyncRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/website-editor/publish":{"post":{"tags":["Website Editor"],"summary":"Publish Website Pages","description":"Deploy edited pages to the LIVE website. Real visitors see it immediately.\n\nGoes to the org's own hosting account when one is connected with a\nproject, otherwise to the graph8-hosted site. Omit `page_ids` to publish\nevery page that has HTML. Spends no credit; it is outward-facing and tiered\nthat way.\n\nSpends nothing.","operationId":"publish_website_pages_website_editor_publish_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WebsiteEditorPublishRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/website-editor/pages/{page_id}/clone":{"post":{"tags":["Website Editor"],"summary":"Clone Website Page","description":"Fetch a page's live HTML so it can be edited. FREE.\n\nFor pages imported by URL rather than synced from a hosting project. A\npage that already has HTML answers `already_cloned` and is not re-fetched.","operationId":"clone_website_page_website_editor_pages__page_id__clone_post","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","description":"Website page id, from `GET /content-workspace/pages`.","title":"Page Id"},"description":"Website page id, from `GET /content-workspace/pages`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/website-editor/pages/{page_id}/update-text":{"post":{"tags":["Website Editor"],"summary":"Update Website Page Text","description":"Set one element's text. FREE - no model runs.\n\n`element_id` is the element's `data-g8-id`. Saved as a new version, so\n`/restore-version` can undo it. Nothing goes live until `/publish`.","operationId":"update_website_page_text_website_editor_pages__page_id__update_text_post","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","description":"Website page id, from `GET /content-workspace/pages`.","title":"Page Id"},"description":"Website page id, from `GET /content-workspace/pages`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WebsiteEditorUpdateTextRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/website-editor/pages/{page_id}/ops":{"post":{"tags":["Website Editor"],"summary":"Apply Website Page Operations","description":"Apply an ordered list of deterministic edit operations. FREE - no model runs.\n\nSend `base_version` (the page's version when you read it) to get a 409\ninstead of overwriting a newer edit. `save_mode: \"save\"` also records a\nrestorable version; `autosave` only updates the page.","operationId":"apply_website_page_operations_website_editor_pages__page_id__ops_post","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","description":"Website page id, from `GET /content-workspace/pages`.","title":"Page Id"},"description":"Website page id, from `GET /content-workspace/pages`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WebsiteEditorPageOpsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/website-editor/pages/{page_id}/versions":{"get":{"tags":["Website Editor"],"summary":"List Website Page Versions","description":"The page's saved versions, newest first. FREE.","operationId":"list_website_page_versions_website_editor_pages__page_id__versions_get","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","description":"Website page id, from `GET /content-workspace/pages`.","title":"Page Id"},"description":"Website page id, from `GET /content-workspace/pages`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/website-editor/pages/{page_id}/restore-version":{"post":{"tags":["Website Editor"],"summary":"Restore Website Page Version","description":"Roll the page back to a saved version. FREE. Not live until `/publish`.","operationId":"restore_website_page_version_website_editor_pages__page_id__restore_version_post","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","description":"Website page id, from `GET /content-workspace/pages`.","title":"Page Id"},"description":"Website page id, from `GET /content-workspace/pages`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WebsiteEditorRestoreVersionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/website-editor/pages/{page_id}/conversation":{"get":{"tags":["Website Editor"],"summary":"Get Website Page Conversation","description":"The AI edit conversation recorded against this page. FREE.","operationId":"get_website_page_conversation_website_editor_pages__page_id__conversation_get","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","description":"Website page id, from `GET /content-workspace/pages`.","title":"Page Id"},"description":"Website page id, from `GET /content-workspace/pages`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/programmatic-campaigns":{"post":{"tags":["Programmatic Pages"],"summary":"Create Programmatic Campaign","description":"Create a programmatic campaign from a template page and a source. FREE.\n\nNothing is generated yet - `POST /{id}/preview` renders one row, and\n`POST /{id}/generate` renders them all. `created_by` is the key's principal.","operationId":"create_programmatic_campaign_programmatic_campaigns_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateProgrammaticCampaignRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"get":{"tags":["Programmatic Pages"],"summary":"List Programmatic Campaigns","description":"Every programmatic campaign in the org, with its generation counters. FREE.","operationId":"list_programmatic_campaigns_programmatic_campaigns_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/programmatic-campaigns/{campaign_id}":{"get":{"tags":["Programmatic Pages"],"summary":"Get Programmatic Campaign","description":"One programmatic campaign. FREE.","operationId":"get_programmatic_campaign_programmatic_campaigns__campaign_id__get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Programmatic campaign id.","title":"Campaign Id"},"description":"Programmatic campaign id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Programmatic Pages"],"summary":"Update Programmatic Campaign","description":"Partial update. FREE. A source or template change marks the pages stale.","operationId":"update_programmatic_campaign_programmatic_campaigns__campaign_id__patch","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Programmatic campaign id.","title":"Campaign Id"},"description":"Programmatic campaign id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateProgrammaticCampaignRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Programmatic Pages"],"summary":"Delete Programmatic Campaign","description":"Delete the campaign and its generated pages.\n\nSpends nothing.","operationId":"delete_programmatic_campaign_programmatic_campaigns__campaign_id__delete","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Programmatic campaign id.","title":"Campaign Id"},"description":"Programmatic campaign id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/programmatic-campaigns/{campaign_id}/variables":{"get":{"tags":["Programmatic Pages"],"summary":"Get Programmatic Campaign Variables","description":"The template's `{{variables}}` and the source columns they can bind to. FREE.","operationId":"get_programmatic_campaign_variables_programmatic_campaigns__campaign_id__variables_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Programmatic campaign id.","title":"Campaign Id"},"description":"Programmatic campaign id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/programmatic-campaigns/{campaign_id}/preview":{"post":{"tags":["Programmatic Pages"],"summary":"Preview Programmatic Page","description":"Render ONE page for one source row, without saving it. FREE.","operationId":"preview_programmatic_page_programmatic_campaigns__campaign_id__preview_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Programmatic campaign id.","title":"Campaign Id"},"description":"Programmatic campaign id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProgrammaticPreviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/programmatic-campaigns/{campaign_id}/generate":{"post":{"tags":["Programmatic Pages"],"summary":"Start Programmatic Generation","description":"Render every page, one per source row, in the background. FREE - no model runs.\n\nPages are generated as drafts; nothing goes live until a deploy action.\n400 if a run is already in progress or the source is empty. Poll\n`GET /{campaign_id}/status`.","operationId":"start_programmatic_generation_programmatic_campaigns__campaign_id__generate_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Programmatic campaign id.","title":"Campaign Id"},"description":"Programmatic campaign id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/programmatic-campaigns/{campaign_id}/status":{"get":{"tags":["Programmatic Pages"],"summary":"Get Programmatic Generation Status","description":"Generation progress: pages generated, failed, total. FREE - the poll target.","operationId":"get_programmatic_generation_status_programmatic_campaigns__campaign_id__status_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Programmatic campaign id.","title":"Campaign Id"},"description":"Programmatic campaign id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/programmatic-campaigns/{campaign_id}/pages":{"get":{"tags":["Programmatic Pages"],"summary":"List Programmatic Generated Pages","description":"The generated pages, a page of results at a time. FREE.","operationId":"list_programmatic_generated_pages_programmatic_campaigns__campaign_id__pages_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Programmatic campaign id.","title":"Campaign Id"},"description":"Programmatic campaign id."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/programmatic-campaigns/{campaign_id}/workspace":{"get":{"tags":["Programmatic Pages"],"summary":"Get Programmatic Workspace","description":"The full workspace: source, template settings, lifecycle state, page summary,\nand the valid row and bulk actions. FREE.","operationId":"get_programmatic_workspace_programmatic_campaigns__campaign_id__workspace_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Programmatic campaign id.","title":"Campaign Id"},"description":"Programmatic campaign id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Programmatic Pages"],"summary":"Update Programmatic Workspace","description":"Update workspace settings - source, SEO, linking, deployment, regeneration. FREE.","operationId":"update_programmatic_workspace_programmatic_campaigns__campaign_id__workspace_patch","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Programmatic campaign id.","title":"Campaign Id"},"description":"Programmatic campaign id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProgrammaticWorkspaceUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/programmatic-campaigns/{campaign_id}/imports/sitemap":{"post":{"tags":["Programmatic Pages"],"summary":"Import Programmatic Sitemap","description":"Make an existing sitemap the campaign's data source. FREE.\n\nUp to `max_urls` URLs become rows of a new source table; `fetch_pages`\nalso fetches each page. REPLACES the campaign's current source.","operationId":"import_programmatic_sitemap_programmatic_campaigns__campaign_id__imports_sitemap_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Programmatic campaign id.","title":"Campaign Id"},"description":"Programmatic campaign id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProgrammaticSitemapImportRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/programmatic-campaigns/{campaign_id}/pages/actions":{"post":{"tags":["Programmatic Pages"],"summary":"Run Programmatic Bulk Page Action","description":"Run a lifecycle action on selected pages - or deploy. CAN CHANGE THE LIVE SITE.\n\n`deploy_pending_changes`, `republish_all`, `rollback_publish` and\n`unpublish_selected` change what real visitors see; `delete_selected`\nremoves pages. `export_urls` only reads.\n\nSpends nothing.","operationId":"run_programmatic_bulk_page_action_programmatic_campaigns__campaign_id__pages_actions_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Programmatic campaign id.","title":"Campaign Id"},"description":"Programmatic campaign id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProgrammaticBulkPageActionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/programmatic-campaigns/{campaign_id}/pages/{page_id}/actions":{"post":{"tags":["Programmatic Pages"],"summary":"Run Programmatic Page Action","description":"Run a lifecycle action on one page. `unpublish` takes it OFF the live site.\n\n`override` replaces the page's rendered HTML with `html_output` (sanitised by\nthe app); `reset_override` returns it to the template.\n\nSpends nothing.","operationId":"run_programmatic_page_action_programmatic_campaigns__campaign_id__pages__page_id__actions_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Programmatic campaign id.","title":"Campaign Id"},"description":"Programmatic campaign id."},{"name":"page_id","in":"path","required":true,"schema":{"type":"string","description":"Generated page id, from `GET .../pages`.","title":"Page Id"},"description":"Generated page id, from `GET .../pages`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProgrammaticPageActionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/library/documents/{doc_id}":{"get":{"tags":["Library"],"summary":"Get Library Document","description":"One document with its extracted text. FREE.","operationId":"get_library_document_library_documents__doc_id__get","parameters":[{"name":"doc_id","in":"path","required":true,"schema":{"type":"string","description":"Library document id.","title":"Doc Id"},"description":"Library document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"},"put":{"tags":["Library"],"summary":"Update Library Document","description":"Update a document's name, folder, metadata or text. FREE. New text is re-embedded.","operationId":"update_library_document_library_documents__doc_id__put","parameters":[{"name":"doc_id","in":"path","required":true,"schema":{"type":"string","description":"Library document id.","title":"Doc Id"},"description":"Library document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateLibraryDocumentRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Library"],"summary":"Delete Library Document","description":"Soft-delete a document. It leaves retrieval; `POST .../restore` brings it back.\n\nSpends nothing.","operationId":"delete_library_document_library_documents__doc_id__delete","parameters":[{"name":"doc_id","in":"path","required":true,"schema":{"type":"string","description":"Library document id.","title":"Doc Id"},"description":"Library document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"knowledge:delete","x-graph8-lifecycle":"active"}},"/library/documents/{doc_id}/download":{"get":{"tags":["Library"],"summary":"Download Library Document","description":"The document's original file, as uploaded. FREE.\n\nNOT wrapped in the JSON envelope: the body is the file itself, with its own\n`Content-Type` and a `Content-Disposition: attachment` filename.","operationId":"download_library_document_library_documents__doc_id__download_get","parameters":[{"name":"doc_id","in":"path","required":true,"schema":{"type":"string","description":"Library document id.","title":"Doc Id"},"description":"Library document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"The file.","content":{"application/octet-stream":{}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/library/documents/{doc_id}/restore":{"post":{"tags":["Library"],"summary":"Restore Library Document","description":"Undo a delete. FREE.","operationId":"restore_library_document_library_documents__doc_id__restore_post","parameters":[{"name":"doc_id","in":"path","required":true,"schema":{"type":"string","description":"Library document id.","title":"Doc Id"},"description":"Library document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/library/documents/{doc_id}/reextract":{"post":{"tags":["Library"],"summary":"Reextract Library Document","description":"Re-read the text out of a stored PDF/DOCX and re-embed it. FREE - no model runs.","operationId":"reextract_library_document_library_documents__doc_id__reextract_post","parameters":[{"name":"doc_id","in":"path","required":true,"schema":{"type":"string","description":"Library document id.","title":"Doc Id"},"description":"Library document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/library/documents/{doc_id}/refresh":{"post":{"tags":["Library"],"summary":"Refresh Library Document","description":"Re-scrape a document that came from a web page, and re-embed it. FREE.\n\nOnly for documents whose `source` is `scrape` (400 otherwise).","operationId":"refresh_library_document_library_documents__doc_id__refresh_post","parameters":[{"name":"doc_id","in":"path","required":true,"schema":{"type":"string","description":"Library document id.","title":"Doc Id"},"description":"Library document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/library/reextract-all":{"post":{"tags":["Library"],"summary":"Reextract All Library Documents","description":"Re-read and re-embed every stored PDF/DOCX. FREE - no model runs.","operationId":"reextract_all_library_documents_library_reextract_all_post","parameters":[{"name":"folder_path","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only this folder. Omit for every PDF/DOCX.","title":"Folder Path"},"description":"Only this folder. Omit for every PDF/DOCX."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/library/case-studies/backfill":{"post":{"tags":["Library"],"summary":"Backfill Library Case Studies","description":"Extract company, industry and results from every case study. SPENDS CREDIT.\n\nA model reads each document in the case-study folders, in the background.\nWithout `force`, documents already processed are skipped.","operationId":"backfill_library_case_studies_library_case_studies_backfill_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BackfillCaseStudiesRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"knowledge:run","x-graph8-lifecycle":"active"}},"/content-workspace/import/crawl":{"post":{"tags":["Content"],"summary":"Start Content Crawl Import","description":"Deep-crawl the org's own website into the workspace. SPENDS PROVIDER CREDIT.\n\nBilled per page crawled; `max_pages` is the ceiling on the spend. Only the\norg's registered website can be crawled. Returns the import job - poll\n`GET /content-workspace/import/status/{job_id}`.","operationId":"start_content_crawl_import_content_workspace_import_crawl_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContentWorkspaceCrawlRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/content-workspace/import/sitemap":{"post":{"tags":["Content"],"summary":"Start Content Sitemap Import","description":"Import the pages an XML sitemap lists. FREE. Returns the import job to poll.","operationId":"start_content_sitemap_import_content_workspace_import_sitemap_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContentWorkspaceSitemapImportRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/content-workspace/import/status/{job_id}":{"get":{"tags":["Content"],"summary":"Get Content Import Status","description":"One import job's progress: found, scraped, imported, skipped, failed. FREE.","operationId":"get_content_import_status_content_workspace_import_status__job_id__get","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","description":"Import job id (UUID).","title":"Job Id"},"description":"Import job id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/content-workspace/import/jobs":{"get":{"tags":["Content"],"summary":"List Content Import Jobs","description":"The org's recent import jobs, newest first. FREE.","operationId":"list_content_import_jobs_content_workspace_import_jobs_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only jobs in this status.","title":"Status"},"description":"Only jobs in this status."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":20,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/content-workspace/seo-summary":{"get":{"tags":["Content"],"summary":"Get Content Seo Summary","description":"Aggregate SEO health: issues by type and severity, average score, score bands. FREE.","operationId":"get_content_seo_summary_content_workspace_seo_summary_get","parameters":[{"name":"domain","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"One owned domain. Omit for all owned pages.","title":"Domain"},"description":"One owned domain. Omit for all owned pages."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/content-workspace/pages":{"get":{"tags":["Content"],"summary":"List Content Workspace Pages","description":"The workspace's pages, filtered and paged. FREE.","operationId":"list_content_workspace_pages_content_workspace_pages_get","parameters":[{"name":"domain","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain"}},{"name":"refresh_status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Refresh Status"}},{"name":"intent","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Intent"}},{"name":"page_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Page Type"}},{"name":"llm_cited","in":"query","required":false,"schema":{"anyOf":[{"type":"boolean"},{"type":"null"}],"description":"Only pages AI answer engines cite (or do not).","title":"Llm Cited"},"description":"Only pages AI answer engines cite (or do not)."},{"name":"ai_overview_present","in":"query","required":false,"schema":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Ai Overview Present"}},{"name":"import_job_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only pages one import brought in.","title":"Import Job Id"},"description":"Only pages one import brought in."},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Search"}},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Page Size"}},{"name":"sort_by","in":"query","required":false,"schema":{"type":"string","description":"Field to sort by.","default":"priority_score","title":"Sort By"},"description":"Field to sort by."},{"name":"sort_order","in":"query","required":false,"schema":{"type":"string","pattern":"^(asc|desc)$","default":"desc","title":"Sort Order"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/content-workspace/pages/{page_id}":{"get":{"tags":["Content"],"summary":"Get Content Workspace Page","description":"One page with its SEO analysis and planning fields. FREE.","operationId":"get_content_workspace_page_content_workspace_pages__page_id__get","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","description":"Content page id (UUID).","title":"Page Id"},"description":"Content page id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Content"],"summary":"Update Content Workspace Page","description":"Update a page's refresh-planning fields. FREE. Only the fields you send change.","operationId":"update_content_workspace_page_content_workspace_pages__page_id__patch","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","description":"Content page id (UUID).","title":"Page Id"},"description":"Content page id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContentWorkspacePageUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Content"],"summary":"Delete Content Workspace Page","description":"Delete a page from the workspace. The live website is not touched.\n\nSpends nothing.","operationId":"delete_content_workspace_page_content_workspace_pages__page_id__delete","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","description":"Content page id (UUID).","title":"Page Id"},"description":"Content page id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/document-versions/{document_type}/{document_id}":{"get":{"tags":["Studio Documents"],"summary":"List Document Versions","description":"A document's saved versions, newest first. FREE.","operationId":"list_document_versions_document_versions__document_type___document_id__get","parameters":[{"name":"document_type","in":"path","required":true,"schema":{"enum":["library","global_context","research","tam","campaign_document"],"type":"string","description":"Which kind of document the id belongs to.","title":"Document Type"},"description":"Which kind of document the id belongs to."},{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Document Id"},"description":"Document id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/document-versions/{document_type}/{document_id}/current":{"get":{"tags":["Studio Documents"],"summary":"Get Current Document Version","description":"The document's current version number. FREE.","operationId":"get_current_document_version_document_versions__document_type___document_id__current_get","parameters":[{"name":"document_type","in":"path","required":true,"schema":{"enum":["library","global_context","research","tam","campaign_document"],"type":"string","description":"Which kind of document the id belongs to.","title":"Document Type"},"description":"Which kind of document the id belongs to."},{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Document Id"},"description":"Document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/document-versions/{document_type}/{document_id}/compare":{"get":{"tags":["Studio Documents"],"summary":"Compare Document Versions","description":"A unified text diff between two versions. FREE. Very large diffs are truncated.","operationId":"compare_document_versions_document_versions__document_type___document_id__compare_get","parameters":[{"name":"document_type","in":"path","required":true,"schema":{"enum":["library","global_context","research","tam","campaign_document"],"type":"string","description":"Which kind of document the id belongs to.","title":"Document Type"},"description":"Which kind of document the id belongs to."},{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Document Id"},"description":"Document id."},{"name":"from","in":"query","required":true,"schema":{"type":"integer","minimum":1,"description":"The older version number.","title":"From"},"description":"The older version number."},{"name":"to","in":"query","required":false,"schema":{"type":"string","maxLength":32,"description":"A version number, or `current`.","default":"current","title":"To"},"description":"A version number, or `current`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/document-versions/{document_type}/{document_id}/{version_number}":{"get":{"tags":["Studio Documents"],"summary":"Get Document Version","description":"One saved version's full content. FREE.","operationId":"get_document_version_document_versions__document_type___document_id___version_number__get","parameters":[{"name":"document_type","in":"path","required":true,"schema":{"enum":["library","global_context","research","tam","campaign_document"],"type":"string","description":"Which kind of document the id belongs to.","title":"Document Type"},"description":"Which kind of document the id belongs to."},{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Document Id"},"description":"Document id."},{"name":"version_number","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Version number, from the history.","title":"Version Number"},"description":"Version number, from the history."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/document-versions/{document_type}/{document_id}/revert/{version_number}":{"post":{"tags":["Studio Documents"],"summary":"Revert Document Version","description":"Restore a saved version as the document's content. FREE.\n\nThe revert is itself recorded as a new version, so it can be undone.\nEverything generated from the document afterwards uses the restored text.","operationId":"revert_document_version_document_versions__document_type___document_id__revert__version_number__post","parameters":[{"name":"document_type","in":"path","required":true,"schema":{"enum":["library","global_context","research","tam","campaign_document"],"type":"string","description":"Which kind of document the id belongs to.","title":"Document Type"},"description":"Which kind of document the id belongs to."},{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Document Id"},"description":"Document id."},{"name":"version_number","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Version number, from the history.","title":"Version Number"},"description":"Version number, from the history."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/DocumentRevertRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/style/normalize":{"post":{"tags":["Studio Documents"],"summary":"Normalize Text To Style","description":"Apply the org's writing-style rules (brand-name casing and the like) to a text. FREE.\n\nDeterministic - no model runs. The same normalisation generation applies.","operationId":"normalize_text_to_style_style_normalize_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StyleNormalizeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/style/rules":{"get":{"tags":["Studio Documents"],"summary":"Get Style Rules","description":"The org's parsed writing-style rules. FREE.","operationId":"get_style_rules_style_rules_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/org/brand-snapshot":{"get":{"tags":["Studio Documents"],"summary":"Get Brand Snapshot","description":"The brand captured from the org's website: design tokens, logo, images. FREE.\n\n404 until a capture has run - `POST /org/brand-snapshot/refresh` starts one.","operationId":"get_brand_snapshot_org_brand_snapshot_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/org/brand-snapshot/refresh":{"post":{"tags":["Studio Documents"],"summary":"Refresh Brand Snapshot","description":"Re-capture the brand from the org's website. SPENDS PROVIDER CREDIT.\n\nA background job scrapes the site through a paid scraping provider.\nReturns a task id.","operationId":"refresh_brand_snapshot_org_brand_snapshot_refresh_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/copilot/chat":{"post":{"tags":["Copilot"],"summary":"Chat With Copilot","description":"Ask the Studio copilot. SPENDS CREDIT - a model runs, and may call tools.\n\nReturns `response` (the full answer) and `events` (every text, tool and\nsource event, in order). `web_search`, `thinking` and `research` each add\nwork and cost; `research` the most. Tools that need a person's approval\nare proposed in `events`, not executed. 402 when the org is out of credit.","operationId":"chat_with_copilot_copilot_chat_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CopilotChatRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"knowledge:run","x-graph8-lifecycle":"active"}},"/copilot/tools":{"get":{"tags":["Copilot"],"summary":"List Copilot Tools","description":"The tools the copilot can call, and which of them need a person's approval. FREE.","operationId":"list_copilot_tools_copilot_tools_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/copilot/mention-search":{"post":{"tags":["Copilot"],"summary":"Search Copilot Mentions","description":"Find what can be @mentioned: documents, personas, ICPs, campaigns, teammates. FREE.\n\nRead-only. Pass results as `mentions` on `POST /copilot/chat`.","operationId":"search_copilot_mentions_copilot_mention_search_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CopilotMentionSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/copilot/landing-page-action":{"post":{"tags":["Copilot"],"summary":"Run Copilot Landing Page Action","description":"Add, remove, reorder or AI-edit a landing page's sections. `edit_section` SPENDS CREDIT.\n\n`add_section`, `remove_section` and `reorder_sections` are deterministic.\nReturns the updated page.","operationId":"run_copilot_landing_page_action_copilot_landing_page_action_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CopilotLandingPageActionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"knowledge:run","x-graph8-lifecycle":"active"}},"/repos/{repo_id}/kb/search":{"post":{"tags":["Knowledge Base"],"summary":"Search Kb","description":"Search the GTM knowledge base using full-text search.","operationId":"search_kb_repos__repo_id__kb_search_post","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/KBSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/repos/{repo_id}/kb":{"get":{"tags":["Knowledge Base"],"summary":"List Kb Documents","description":"List all KB documents grouped by section.","operationId":"list_kb_documents_repos__repo_id__kb_get","parameters":[{"name":"repo_id","in":"path","required":true,"schema":{"type":"string","description":"Repository ID","title":"Repo Id"},"description":"Repository ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/knowledge":{"get":{"tags":["Knowledge"],"summary":"List Knowledge","operationId":"list_knowledge_knowledge_get","parameters":[{"name":"concept_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Concept Type"}},{"name":"lifecycle","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":32},{"type":"null"}],"title":"Lifecycle"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/knowledge/search":{"get":{"tags":["Knowledge"],"summary":"Search Knowledge","operationId":"search_knowledge_knowledge_search_get","parameters":[{"name":"query","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":1000,"title":"Query"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"default":10,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/knowledge/context":{"post":{"tags":["Knowledge"],"summary":"Assemble Knowledge Context","operationId":"assemble_knowledge_context_knowledge_context_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/KnowledgeContextRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/knowledge/export":{"get":{"tags":["Knowledge"],"summary":"Export Knowledge","operationId":"export_knowledge_knowledge_export_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/knowledge/{concept_id}":{"get":{"tags":["Knowledge"],"summary":"Get Knowledge","operationId":"get_knowledge_knowledge__concept_id__get","parameters":[{"name":"concept_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"title":"Concept Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/knowledge/{concept_id}/related":{"get":{"tags":["Knowledge"],"summary":"Related Knowledge","operationId":"related_knowledge_knowledge__concept_id__related_get","parameters":[{"name":"concept_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"title":"Concept Id"}},{"name":"depth","in":"query","required":false,"schema":{"type":"integer","maximum":3,"minimum":1,"default":1,"title":"Depth"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"default":25,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/knowledge/{concept_id}/sources":{"get":{"tags":["Knowledge"],"summary":"Knowledge Sources","operationId":"knowledge_sources_knowledge__concept_id__sources_get","parameters":[{"name":"concept_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"title":"Concept Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/public/enrich/lookup":{"post":{"tags":["Public"],"summary":"Public Enrich Lookup","description":"Look up a contact by email using write key authentication.\n\nUsed by the <G8Form /> progressive form component to determine which\nfields graph8 already knows (and can hide) vs which fields to ask the user.\n\nSearches the mashup (OpenSearch) index for enrichment data.","operationId":"public_enrich_lookup_public_enrich_lookup_post","parameters":[{"name":"X-Write-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Write-Key"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PublicEnrichRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PublicEnrichResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-lifecycle":"active"}},"/visitors/streams":{"get":{"tags":["Visitors"],"summary":"Get Visitor Workspace","description":"The tracking workspace: its streams and their public write keys.\n\nThe write keys are what the browser snippet sends with, so this is the\nendpoint a rebuilt install flow reads to render the snippet.","operationId":"get_visitor_workspace_visitors_streams_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VisitorStreamsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/streams/list":{"get":{"tags":["Visitors"],"summary":"List Visitor Streams","description":"Just the streams, without the surrounding workspace payload.","operationId":"list_visitor_streams_visitors_streams_list_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VisitorStreamsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/page-hosts":{"get":{"tags":["Visitors"],"summary":"List Visitor Page Hosts","description":"Hostnames the snippet has actually reported from.\n\nUseful for catching a snippet installed on a staging domain, or missing\nfrom one you expected.","operationId":"list_visitor_page_hosts_visitors_page_hosts_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/live":{"get":{"tags":["Visitors"],"summary":"Get Live Visitors","description":"Raw live sessions in the window.\n\nIdentifying fields are REDACTED unless the key's user holds a Signals\nwrite capability - the same rule the browser applies, resolved from the\nsame principal.","operationId":"get_live_visitors_visitors_live_get","parameters":[{"name":"time_window","in":"query","required":false,"schema":{"enum":["5min","30min","1hr"],"type":"string","description":"Live window.","default":"30min","title":"Time Window"},"description":"Live window."},{"name":"stream_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys, or \"all\". Omit for every stream.","title":"Stream Id"},"description":"Comma-separated public keys, or \"all\". Omit for every stream."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":10000,"minimum":1,"default":10000,"title":"Limit"}},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Also count bot and crawler traffic. Off by default: events from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded.","default":false,"title":"Include Bots"},"description":"Also count bot and crawler traffic. Off by default: events from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Also count internal traffic. Off by default: the graph8 app (app.graph8.com), local development hosts and your own team members (member emails and company email domains) are excluded.","default":false,"title":"Include Internal"},"description":"Also count internal traffic. Off by default: the graph8 app (app.graph8.com), local development hosts and your own team members (member emails and company email domains) are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/live/aggregated":{"get":{"tags":["Visitors"],"summary":"Get Aggregated Live Visitors","description":"Live sessions rolled up per visitor. Same PII rule as `/live`.","operationId":"get_aggregated_live_visitors_visitors_live_aggregated_get","parameters":[{"name":"time_window","in":"query","required":false,"schema":{"enum":["5min","30min","1hr"],"type":"string","description":"Live window.","default":"30min","title":"Time Window"},"description":"Live window."},{"name":"stream_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys, or \"all\". Omit for every stream.","title":"Stream Id"},"description":"Comma-separated public keys, or \"all\". Omit for every stream."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":5000,"minimum":1,"default":1000,"title":"Limit"}},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Also count bot and crawler traffic. Off by default: events from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded.","default":false,"title":"Include Bots"},"description":"Also count bot and crawler traffic. Off by default: events from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Also count internal traffic. Off by default: the graph8 app (app.graph8.com), local development hosts and your own team members (member emails and company email domains) are excluded.","default":false,"title":"Include Internal"},"description":"Also count internal traffic. Off by default: the graph8 app (app.graph8.com), local development hosts and your own team members (member emails and company email domains) are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/contacts/events":{"get":{"tags":["Visitors"],"summary":"List Contact Visitor Events","description":"Visits attributed to a known contact.\n\nCarries BOTH gates the app declares: Signals read AND Contacts read. This\nfeed joins website behaviour to identified people, so holding one without\nthe other is not enough - and dropping either would be a quieter leak than\nit looks.","operationId":"list_contact_visitor_events_visitors_contacts_events_get","parameters":[{"name":"show_mode","in":"query","required":false,"schema":{"enum":["grouped","raw"],"type":"string","default":"grouped","title":"Show Mode"}},{"name":"filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Serialised filter expression, passed through to the events query unchanged. Its grammar is the app's, not this contract's - a typed model here would freeze a filter language that still moves.","title":"Filter"},"description":"Serialised filter expression, passed through to the events query unchanged. Its grammar is the app's, not this contract's - a typed model here would freeze a filter language that still moves."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (1-indexed).","default":1,"title":"Page"},"description":"Page number (1-indexed)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page.","default":50,"title":"Limit"},"description":"Items per page."},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Also count bot and crawler traffic. Off by default: events from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded.","default":false,"title":"Include Bots"},"description":"Also count bot and crawler traffic. Off by default: events from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Also count internal traffic. Off by default: the graph8 app (app.graph8.com), local development hosts and your own team members (member emails and company email domains) are excluded.","default":false,"title":"Include Internal"},"description":"Also count internal traffic. Off by default: the graph8 app (app.graph8.com), local development hosts and your own team members (member emails and company email domains) are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VisitorEventPage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/contacts/b2bc/events":{"get":{"tags":["Visitors"],"summary":"List B2Bc Contact Visitor Events","description":"The B2BC variant of the contact feed.","operationId":"list_b2bc_contact_visitor_events_visitors_contacts_b2bc_events_get","parameters":[{"name":"show_mode","in":"query","required":false,"schema":{"enum":["grouped","raw"],"type":"string","default":"grouped","title":"Show Mode"}},{"name":"filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Serialised filter expression, passed through to the events query unchanged. Its grammar is the app's, not this contract's - a typed model here would freeze a filter language that still moves.","title":"Filter"},"description":"Serialised filter expression, passed through to the events query unchanged. Its grammar is the app's, not this contract's - a typed model here would freeze a filter language that still moves."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (1-indexed).","default":1,"title":"Page"},"description":"Page number (1-indexed)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page.","default":50,"title":"Limit"},"description":"Items per page."},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Also count bot and crawler traffic. Off by default: events from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded.","default":false,"title":"Include Bots"},"description":"Also count bot and crawler traffic. Off by default: events from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Also count internal traffic. Off by default: the graph8 app (app.graph8.com), local development hosts and your own team members (member emails and company email domains) are excluded.","default":false,"title":"Include Internal"},"description":"Also count internal traffic. Off by default: the graph8 app (app.graph8.com), local development hosts and your own team members (member emails and company email domains) are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VisitorEventPage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/companies/events":{"get":{"tags":["Visitors"],"summary":"List Company Visitor Events","description":"Visits resolved to a company rather than a person.","operationId":"list_company_visitor_events_visitors_companies_events_get","parameters":[{"name":"show_mode","in":"query","required":false,"schema":{"enum":["grouped","raw"],"type":"string","default":"grouped","title":"Show Mode"}},{"name":"filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Serialised filter expression, passed through to the events query unchanged. Its grammar is the app's, not this contract's - a typed model here would freeze a filter language that still moves.","title":"Filter"},"description":"Serialised filter expression, passed through to the events query unchanged. Its grammar is the app's, not this contract's - a typed model here would freeze a filter language that still moves."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (1-indexed).","default":1,"title":"Page"},"description":"Page number (1-indexed)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page.","default":50,"title":"Limit"},"description":"Items per page."},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Also count bot and crawler traffic. Off by default: events from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded.","default":false,"title":"Include Bots"},"description":"Also count bot and crawler traffic. Off by default: events from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Also count internal traffic. Off by default: the graph8 app (app.graph8.com), local development hosts and your own team members (member emails and company email domains) are excluded.","default":false,"title":"Include Internal"},"description":"Also count internal traffic. Off by default: the graph8 app (app.graph8.com), local development hosts and your own team members (member emails and company email domains) are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VisitorEventPage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/campaigns/events":{"get":{"tags":["Visitors"],"summary":"List Campaign Visitor Events","description":"Visits attributed to a sequence.","operationId":"list_campaign_visitor_events_visitors_campaigns_events_get","parameters":[{"name":"campaign","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Sequence id to scope to, or \"all\"/omitted for none. When set it ALWAYS constrains results to that campaign's sequencer steps: a step filter can only narrow within the campaign, never broaden to others, and a step belonging to a different campaign is rejected.","title":"Campaign"},"description":"Sequence id to scope to, or \"all\"/omitted for none. When set it ALWAYS constrains results to that campaign's sequencer steps: a step filter can only narrow within the campaign, never broaden to others, and a step belonging to a different campaign is rejected."},{"name":"filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Serialised filter expression, passed through to the events query unchanged. Its grammar is the app's, not this contract's - a typed model here would freeze a filter language that still moves.","title":"Filter"},"description":"Serialised filter expression, passed through to the events query unchanged. Its grammar is the app's, not this contract's - a typed model here would freeze a filter language that still moves."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (1-indexed).","default":1,"title":"Page"},"description":"Page number (1-indexed)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page.","default":50,"title":"Limit"},"description":"Items per page."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VisitorEventPage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/ads/events":{"get":{"tags":["Visitors"],"summary":"List Ad Visitor Events","description":"Visits attributed to an ad.","operationId":"list_ad_visitor_events_visitors_ads_events_get","parameters":[{"name":"filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Serialised filter expression, passed through to the events query unchanged. Its grammar is the app's, not this contract's - a typed model here would freeze a filter language that still moves.","title":"Filter"},"description":"Serialised filter expression, passed through to the events query unchanged. Its grammar is the app's, not this contract's - a typed model here would freeze a filter language that still moves."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (1-indexed).","default":1,"title":"Page"},"description":"Page number (1-indexed)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page.","default":50,"title":"Limit"},"description":"Items per page."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VisitorEventPage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/links/events":{"get":{"tags":["Visitors"],"summary":"List Link Visitor Events","description":"Clicks on a tracked link.","operationId":"list_link_visitor_events_visitors_links_events_get","parameters":[{"name":"filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Serialised filter expression, passed through to the events query unchanged. Its grammar is the app's, not this contract's - a typed model here would freeze a filter language that still moves.","title":"Filter"},"description":"Serialised filter expression, passed through to the events query unchanged. Its grammar is the app's, not this contract's - a typed model here would freeze a filter language that still moves."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (1-indexed).","default":1,"title":"Page"},"description":"Page number (1-indexed)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page.","default":50,"title":"Limit"},"description":"Items per page."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VisitorEventPage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/{resource}/statistics":{"post":{"tags":["Visitors"],"summary":"Get Visitor Statistics","description":"Counts over the visitor stream, filtered.\n\n`companies` counts UNIQUE BY IP, `contacts` does not - the two series are\nnot comparable row for row and should not be charted as if they were.","operationId":"get_visitor_statistics_visitors__resource__statistics_post","parameters":[{"name":"resource","in":"path","required":true,"schema":{"enum":["contacts","companies"],"type":"string","description":"What to count.","title":"Resource"},"description":"What to count."},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Also count bot and crawler traffic. Off by default: events from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded.","default":false,"title":"Include Bots"},"description":"Also count bot and crawler traffic. Off by default: events from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Also count internal traffic. Off by default: the graph8 app (app.graph8.com), local development hosts and your own team members (member emails and company email domains) are excluded.","default":false,"title":"Include Internal"},"description":"Also count internal traffic. Off by default: the graph8 app (app.graph8.com), local development hosts and your own team members (member emails and company email domains) are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"type":"array","items":{"type":"object","additionalProperties":true},"description":"Filter conditions, each `{field, operator, value}` - e.g. `{\"field\": \"received_at\", \"operator\": \"greaterThanOrEqual\", \"value\": \"2025-01-01\"}`. An empty list means no filtering. Left as an open shape because the operator vocabulary is the app's and still moves; an enum here would reject a filter the app accepts.","title":"Conditions"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VisitorStatisticsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"visitors:write","x-graph8-lifecycle":"active"}},"/visitors/{resource}/distinct-browsers":{"get":{"tags":["Visitors"],"summary":"List Visitor Distinct Browsers","description":"Browser values present in the data - a filter picker, not analytics.","operationId":"list_visitor_distinct_browsers_visitors__resource__distinct_browsers_get","parameters":[{"name":"resource","in":"path","required":true,"schema":{"enum":["contacts","companies"],"type":"string","title":"Resource"}},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Scope to a single stream.","title":"Write Key"},"description":"Scope to a single stream."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_str__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/{resource}/distinct-utms":{"get":{"tags":["Visitors"],"summary":"List Visitor Distinct Utms","description":"UTM values present in the data - the other half of the filter picker.","operationId":"list_visitor_distinct_utms_visitors__resource__distinct_utms_get","parameters":[{"name":"resource","in":"path","required":true,"schema":{"enum":["contacts","companies"],"type":"string","title":"Resource"}},{"name":"param","in":"query","required":true,"schema":{"enum":["utm_source","utm_medium","utm_campaign"],"type":"string","description":"Which UTM parameter to list values for.","title":"Param"},"description":"Which UTM parameter to list values for."},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Scope to a single stream.","title":"Write Key"},"description":"Scope to a single stream."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_str__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/contacts-metrics":{"get":{"tags":["Visitors"],"summary":"Get Visitor Contact Metrics","description":"Identified-contact metrics over time.\n\nThe path is `contacts-metrics`, hyphenated, matching every other path on\nthis surface - the app's `contacts_metrics` is the odd one out.","operationId":"get_visitor_contact_metrics_visitors_contacts_metrics_get","parameters":[{"name":"timeframe","in":"query","required":false,"schema":{"type":"string","description":"Preset period.","default":"last_7_days","title":"Timeframe"},"description":"Preset period."},{"name":"interval","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"day | week | month | quarter.","title":"Interval"},"description":"day | week | month | quarter."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Custom start, YYYY-MM-DD.","title":"Start Date"},"description":"Custom start, YYYY-MM-DD."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Custom end, YYYY-MM-DD.","title":"End Date"},"description":"Custom end, YYYY-MM-DD."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/links/build":{"post":{"tags":["Visitors"],"summary":"Build Tracked Link","description":"Mint a tracked short link for a destination URL.\n\nGated on `signals:run`, NOT `signals:read` - this mints a durable public\nURL that attributes real traffic, which is why the app puts it behind the\nrun grant rather than the read one.","operationId":"build_tracked_link_visitors_links_build_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TrackedLinkRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"visitors:write","x-graph8-lifecycle":"active"}},"/visitors/campaigns/list-syncs":{"post":{"tags":["Visitors"],"summary":"Start Campaign List Sync","description":"Sync the website visitors of some campaign steps into their campaign lists.\n\nASYNCHRONOUS: 202 and a `job_id`; poll\n`GET /visitors/campaigns/list-syncs/{job_id}`. While a sync is already\nrunning for the org, the running job comes back with\n`status: already_running` and nothing new starts.","operationId":"start_campaign_list_sync_visitors_campaigns_list_syncs_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VisitorListSyncRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VisitorListSyncJob_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"visitors:write","x-graph8-lifecycle":"active"}},"/visitors/campaigns/list-syncs/{job_id}":{"get":{"tags":["Visitors"],"summary":"Get Campaign List Sync","description":"How a campaign list sync is going: its state and, once done, how many lists it updated.","operationId":"get_campaign_list_sync_visitors_campaigns_list_syncs__job_id__get","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"`job_id` from the sync that started it.","title":"Job Id"},"description":"`job_id` from the sync that started it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VisitorListSyncJob_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/contacts/{contact_id}/events":{"get":{"tags":["Visitors"],"summary":"Get Contact Visitor Events","description":"Every page ONE identified contact viewed on the website, newest first.\n\n`GET /visitors/contacts/events` is the org-wide feed; this is one person's\nhistory and carries the per-record access check. A contact outside the\nkey's scope is a 404, so this cannot be used to probe which ids exist.","operationId":"get_contact_visitor_events_visitors_contacts__contact_id__events_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VisitorContactEvents_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/installation-check":{"get":{"tags":["Visitors"],"summary":"Check Tracking Installation","description":"Is the tracking snippet installed? Answered by whether events are ARRIVING.\n\nAt least one of `write_key` or `host` is required (422 otherwise). Both are\nfilters inside the key's own org - they cannot reach another tenant's\nevents.","operationId":"check_tracking_installation_visitors_installation_check_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"A stream's browser write key (`id:secret`); matched by key id.","title":"Write Key"},"description":"A stream's browser write key (`id:secret`); matched by key id."},{"name":"host","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Website hostname to scope the check to, e.g. example.com.","title":"Host"},"description":"Website hostname to scope the check to, e.g. example.com."},{"name":"since_minutes","in":"query","required":false,"schema":{"type":"integer","maximum":525600,"minimum":1,"description":"Look-back window in minutes (default 30 days).","default":43200,"title":"Since Minutes"},"description":"Look-back window in minutes (default 30 days)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SiteConnectionsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/client-info":{"get":{"tags":["Visitors"],"summary":"Get Tracking Client Info","description":"The browser write key and domains a snippet for this stream should use.\n\nThe key is the PUBLIC browser key embedded in every page the snippet is on,\nnot a secret. An unknown `source_id` falls back to the org default, as the\napp does.","operationId":"get_tracking_client_info_visitors_client_info_get","parameters":[{"name":"source_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"A stream id. Omit for the org's default stream.","title":"Source Id"},"description":"A stream id. Omit for the org's default stream."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SiteConnectionsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"}},"/visitors/form-capture-settings":{"get":{"tags":["Visitors"],"summary":"Get Form Capture Settings","description":"Which hosts and paths form submissions are captured from.\n\nDefaults (capture everywhere, bookings included) when nothing has been set.","operationId":"get_form_capture_settings_visitors_form_capture_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SiteConnectionsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Visitors"],"summary":"Update Form Capture Settings","description":"Replace the form-capture filters. Takes effect for the next submission on the site.\n\nPATCH is the app's verb, but the body is a FULL REPLACEMENT - see the\nrequest model.","operationId":"update_form_capture_settings_visitors_form_capture_settings_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormCaptureSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SiteConnectionsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"visitors:write","x-graph8-lifecycle":"active"}},"/visitors/tailor/query-param-sets":{"get":{"tags":["Visitors"],"summary":"List Tailor Query Param Sets","description":"Saved page-personalisation query-param sets, oldest first, as `sets`.","operationId":"list_tailor_query_param_sets_visitors_tailor_query_param_sets_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SiteConnectionsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"visitors:read","x-graph8-lifecycle":"active"},"post":{"tags":["Visitors"],"summary":"Create Tailor Query Param Set","description":"Save a query-param set. At most ten per org; the eleventh is a 422.","operationId":"create_tailor_query_param_set_visitors_tailor_query_param_sets_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TailorQueryParamSetRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SiteConnectionsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"visitors:write","x-graph8-lifecycle":"active"}},"/visitors/tailor/query-param-sets/{set_id}":{"delete":{"tags":["Visitors"],"summary":"Delete Tailor Query Param Set","description":"Delete one saved set. Another org's id is a 404.","operationId":"delete_tailor_query_param_set_visitors_tailor_query_param_sets__set_id__delete","parameters":[{"name":"set_id","in":"path","required":true,"schema":{"type":"string","description":"The set's id (a UUID).","title":"Set Id"},"description":"The set's id (a UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SiteConnectionsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"visitors:write","x-graph8-lifecycle":"active"}},"/public/visitors/company":{"get":{"tags":["Public - Visitors"],"summary":"Public Visitor Company","description":"Resolve the current visitor's IP address to a company.\n\nUses the ip_2_company ClickHouse table to identify which company\nthe visitor belongs to based on their IP address. Used by g8.visitors.identify().","operationId":"public_visitor_company_public_visitors_company_get","parameters":[{"name":"visitor_ip","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"ipvanyaddress"},{"type":"null"}],"title":"Visitor Ip"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Write-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Write-Key"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VisitorCompanyResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/public/visitors/score":{"get":{"tags":["Public - Visitors"],"summary":"Public Visitor Score","description":"Get engagement score for the current visitor.\n\nScores are based on page views, time on site, and actions taken.\nUsed by g8.visitors.score().","operationId":"public_visitor_score_public_visitors_score_get","parameters":[{"name":"visitor_ip","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"ipvanyaddress"},{"type":"null"}],"title":"Visitor Ip"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Write-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Write-Key"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VisitorScoreResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/public/signals/company":{"get":{"tags":["Public - Signals"],"summary":"Public Signals Company","description":"Get intent signals for a company domain.\n\nAnalyzes visitor behavior from the org's ClickHouse events to determine\nbuying intent. Used by g8.signals.company().","operationId":"public_signals_company_public_signals_company_get","parameters":[{"name":"domain","in":"query","required":true,"schema":{"type":"string","title":"Domain"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Write-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Write-Key"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntentSignalsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/forms/{form_key}/fields":{"get":{"tags":["Forms"],"summary":"Get Form Fields","description":"The fields this form actually submits - what a mapping maps FROM.","operationId":"get_form_fields_forms__form_key__fields_get","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"Form key.","title":"Form Key"},"description":"Form key."},{"name":"source_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":500,"description":"Which INSTALLED SOURCE of this form. Required: a form key can be present on more than one source, and every operation here is scoped to one.","title":"Source Id"},"description":"Which INSTALLED SOURCE of this form. Required: a form key can be present on more than one source, and every operation here is scoped to one."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"forms:read","x-graph8-lifecycle":"active"}},"/forms/{form_key}/placements":{"get":{"tags":["Forms"],"summary":"Get Form Placements","description":"Where this form appears - the pages it has actually been seen on.","operationId":"get_form_placements_forms__form_key__placements_get","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"Form key.","title":"Form Key"},"description":"Form key."},{"name":"source_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":500,"description":"Which INSTALLED SOURCE of this form. Required: a form key can be present on more than one source, and every operation here is scoped to one.","title":"Source Id"},"description":"Which INSTALLED SOURCE of this form. Required: a form key can be present on more than one source, and every operation here is scoped to one."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"forms:read","x-graph8-lifecycle":"active"}},"/forms/{form_key}":{"patch":{"tags":["Forms"],"summary":"Update Form Registry","description":"Rename a form, reassign its owner, or archive it.","operationId":"update_form_registry_forms__form_key__patch","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"Form key.","title":"Form Key"},"description":"Form key."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormRegistryPatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"forms:write","x-graph8-lifecycle":"active"}},"/forms/{form_key}/route":{"put":{"tags":["Forms"],"summary":"Save Form Route","description":"Set where this form's submissions go, and how its fields map.\n\nSEND THE `expected_*` PRECONDITIONS. They are optimistic-concurrency\nguards, not settings: without them the save is last-writer-wins and can\nsilently overwrite a colleague's route on a live form.\n\n`workflow_policy` defaults to `disabled`. `simulate` records what WOULD\nhave run without running it, which is the safe way to turn automation on\nfor a form that is already receiving real submissions.","operationId":"save_form_route_forms__form_key__route_put","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"Form key.","title":"Form Key"},"description":"Form key."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormRouteRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"forms:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Forms"],"summary":"Rollback Form Route","description":"Roll the route back, or cancel a pending one.\n\nA DELETE that takes a BODY, matching the app - because this is not \"delete\nthe route\", it is \"move it back\", and which version to move to has to\ntravel with the request. The form keeps routing; it routes as it did\nbefore.","operationId":"rollback_form_route_forms__form_key__route_delete","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"Form key.","title":"Form Key"},"description":"Form key."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormRouteRollbackRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"forms:delete","x-graph8-lifecycle":"active"}},"/forms/{form_key}/route/recommendations":{"get":{"tags":["Forms"],"summary":"Get Form Route Recommendations","description":"Suggested field mappings for this form.","operationId":"get_form_route_recommendations_forms__form_key__route_recommendations_get","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"Form key.","title":"Form Key"},"description":"Form key."},{"name":"source_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":500,"description":"Which INSTALLED SOURCE of this form. Required: a form key can be present on more than one source, and every operation here is scoped to one.","title":"Source Id"},"description":"Which INSTALLED SOURCE of this form. Required: a form key can be present on more than one source, and every operation here is scoped to one."},{"name":"target_list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Destination list to tailor the mapping suggestions to. OPTIONAL on purpose: a caller asks for recommendations BEFORE choosing a destination, and making it required 422s every such request.","title":"Target List Id"},"description":"Destination list to tailor the mapping suggestions to. OPTIONAL on purpose: a caller asks for recommendations BEFORE choosing a destination, and making it required 422s every such request."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"forms:read","x-graph8-lifecycle":"active"}},"/forms/{form_key}/route/test":{"post":{"tags":["Forms"],"summary":"Test Form Route","description":"Run a test submission through the route and report where it landed.\n\nGated on LISTS WRITE, not read, because it exercises the delivery path.","operationId":"test_form_route_forms__form_key__route_test_post","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"Form key.","title":"Form Key"},"description":"Form key."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormSourceScopedRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"forms:write","x-graph8-lifecycle":"active"}},"/forms/{form_key}/delivery/pause":{"post":{"tags":["Forms"],"summary":"Pause Form Delivery","description":"Stop delivering this form's submissions.\n\nThe form keeps ACCEPTING submissions - pausing stops them being routed\nonward, it does not take the form down. They queue rather than vanish.","operationId":"pause_form_delivery_forms__form_key__delivery_pause_post","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"Form key.","title":"Form Key"},"description":"Form key."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormSourceScopedRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"forms:run","x-graph8-lifecycle":"active"}},"/forms/{form_key}/delivery/resume":{"post":{"tags":["Forms"],"summary":"Resume Form Delivery","description":"Start delivering again.","operationId":"resume_form_delivery_forms__form_key__delivery_resume_post","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"Form key.","title":"Form Key"},"description":"Form key."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormSourceScopedRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"forms:run","x-graph8-lifecycle":"active"}},"/forms/deliveries/{receipt_id}/retry":{"post":{"tags":["Forms"],"summary":"Retry Form Delivery","description":"Retry ONE failed delivery.\n\nScoped by receipt rather than by form, so a caller retries the specific\nsubmission that failed instead of replaying everything - which is what the\nbackfill endpoints are for, and why they are not on this surface.\n\nNOTE ON ROUTING ORDER: `/forms/deliveries/...` is a LITERAL first segment\nthat `/forms/{form_key}/...` would otherwise swallow, reading \"deliveries\"\nas a form key. It is declared here, and the shadowing test compares\ncompiled match patterns to keep it that way.","operationId":"retry_form_delivery_forms_deliveries__receipt_id__retry_post","parameters":[{"name":"receipt_id","in":"path","required":true,"schema":{"type":"string","description":"Delivery receipt id from the activity feed.","title":"Receipt Id"},"description":"Delivery receipt id from the activity feed."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"forms:run","x-graph8-lifecycle":"active"}},"/forms/{form_key}/activity":{"get":{"tags":["Forms"],"summary":"Get Form Activity","description":"Recent submissions and what happened to each one.","operationId":"get_form_activity_forms__form_key__activity_get","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"Form key.","title":"Form Key"},"description":"Form key."},{"name":"source_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":500,"description":"Which INSTALLED SOURCE of this form. Required: a form key can be present on more than one source, and every operation here is scoped to one.","title":"Source Id"},"description":"Which INSTALLED SOURCE of this form. Required: a form key can be present on more than one source, and every operation here is scoped to one."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"forms:read","x-graph8-lifecycle":"active"}},"/forms/{form_key}/submissions/{submission_id}/trace":{"get":{"tags":["Forms"],"summary":"Get Form Submission Trace","description":"Follow ONE submission through the route, step by step.\n\nThis is the endpoint that answers \"the customer filled in the form, where\ndid it go\" - the question the whole surface exists for, and the one a\nrebuilt forms UI could not ask without it.","operationId":"get_form_submission_trace_forms__form_key__submissions__submission_id__trace_get","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"Form key.","title":"Form Key"},"description":"Form key."},{"name":"submission_id","in":"path","required":true,"schema":{"type":"string","description":"Submission id from the activity feed.","title":"Submission Id"},"description":"Submission id from the activity feed."},{"name":"source_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":500,"description":"Which INSTALLED SOURCE of this form. Required: a form key can be present on more than one source, and every operation here is scoped to one.","title":"Source Id"},"description":"Which INSTALLED SOURCE of this form. Required: a form key can be present on more than one source, and every operation here is scoped to one."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"forms:read","x-graph8-lifecycle":"active"}},"/forms":{"get":{"tags":["Forms"],"summary":"List Forms","description":"List and search the org's lead-capture forms.\n\nUse ``search`` to find a specific form by name (e.g. \"discovery\"). Each\nitem carries the ``source_id`` and ``form_key`` needed for the overview\nendpoint.","operationId":"list_forms_forms_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"1-indexed page.","default":1,"title":"Page"},"description":"1-indexed page."},{"name":"per_page","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Rows per page (max 200).","default":20,"title":"Per Page"},"description":"Rows per page (max 200)."},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"description":"Case-insensitive substring match on form name/id.","title":"Search"},"description":"Case-insensitive substring match on form name/id."},{"name":"source_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"description":"Filter to a single write key / site.","title":"Source Id"},"description":"Filter to a single write key / site."},{"name":"sort_field","in":"query","required":false,"schema":{"anyOf":[{"enum":["submissions_30d","total_submissions","latest_submitted_at","form_tag_id"],"type":"string"},{"type":"null"}],"description":"total_submissions | latest_submitted_at | form_tag_id","title":"Sort Field"},"description":"total_submissions | latest_submitted_at | form_tag_id"},{"name":"sort_order","in":"query","required":false,"schema":{"anyOf":[{"enum":["asc","desc"],"type":"string"},{"type":"null"}],"description":"asc | desc","title":"Sort Order"},"description":"asc | desc"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"forms:read","x-graph8-lifecycle":"active"}},"/forms/{form_key}/overview":{"get":{"tags":["Forms"],"summary":"Get Form Overview","description":"Per-form operational detail: health, submission metrics, destination.\n\n``source_id`` is required and comes from a ``list_forms`` result — a form\nid is only unique within its source.","operationId":"get_form_overview_forms__form_key__overview_get","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"The form's HTML tag id / group key (from list_forms).","title":"Form Key"},"description":"The form's HTML tag id / group key (from list_forms)."},{"name":"source_id","in":"query","required":true,"schema":{"type":"string","description":"Write key / site the form belongs to (from list_forms).","title":"Source Id"},"description":"Write key / site the form belongs to (from list_forms)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormOverview_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"forms:read","x-graph8-lifecycle":"active"}},"/forms/views/saved":{"get":{"tags":["Forms"],"summary":"List Saved Form Views","description":"Saved filter sets over the form inventory, as `items`.","operationId":"list_saved_form_views_forms_views_saved_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"forms:read","x-graph8-lifecycle":"active"}},"/forms/views/saved/{view_id}":{"put":{"tags":["Forms"],"summary":"Save Form View","description":"Create or replace a saved view. PUT because it is an upsert by id.","operationId":"save_form_view_forms_views_saved__view_id__put","parameters":[{"name":"view_id","in":"path","required":true,"schema":{"type":"string","description":"The view's id. Created when it does not exist.","title":"View Id"},"description":"The view's id. Created when it does not exist."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormSavedViewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"forms:write","x-graph8-lifecycle":"active"}},"/forms/unidentified/grouping":{"get":{"tags":["Forms"],"summary":"Preview Unidentified Grouping","description":"How submissions with no form id WOULD split under each grouping axis.\n\nSome sites render forms with no stable id, so every such submission lands\nin one bucket. Each option carries the numbers behind it, including whether\nit would split one real form apart or merge several together.","operationId":"preview_unidentified_grouping_forms_unidentified_grouping_get","parameters":[{"name":"source_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"One site. Omit for every site.","title":"Source Id"},"description":"One site. Omit for every site."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"forms:read","x-graph8-lifecycle":"active"},"put":{"tags":["Forms"],"summary":"Set Unidentified Grouping","description":"Choose how one site's id-less submissions are split into forms.\n\nApplied at read time, so it regroups HISTORY as well as new traffic: the\nshape of the inventory changes under anything already pointed at it.","operationId":"set_unidentified_grouping_forms_unidentified_grouping_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormGroupingRuleRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"forms:write","x-graph8-lifecycle":"active"}},"/forms/unidentified/groups/sync":{"post":{"tags":["Forms"],"summary":"Sync Unidentified Group","description":"Name one group of id-less submissions and fill a list with its leads.\n\nWrites EVERY matching submission to `target_list_id` before answering;\n`submissions_synced` is the number actually written. Gated twice, as the\napp gates it.","operationId":"sync_unidentified_group_forms_unidentified_groups_sync_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormGroupSyncRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"forms:write","x-graph8-lifecycle":"active"}},"/forms/groups":{"get":{"tags":["Forms"],"summary":"List Form Groups","description":"Curated groups - several inventory rows treated as one form - with their members.","operationId":"list_form_groups_forms_groups_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"forms:read","x-graph8-lifecycle":"active"},"post":{"tags":["Forms"],"summary":"Create Form Group","description":"Treat several inventory rows as one form.\n\nA member already in another group is MOVED here, not copied.","operationId":"create_form_group_forms_groups_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormGroupCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"forms:write","x-graph8-lifecycle":"active"}},"/forms/groups/{group_id}":{"patch":{"tags":["Forms"],"summary":"Update Form Group","description":"Rename or re-type a group. Membership changes through the member routes.","operationId":"update_form_group_forms_groups__group_id__patch","parameters":[{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"The group's id.","title":"Group Id"},"description":"The group's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormGroupPatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"forms:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Forms"],"summary":"Delete Form Group","description":"Ungroup. The members return to standalone inventory rows; no submission is touched.\n\nThe app answers 204 with no body; this answers the id that was removed.","operationId":"delete_form_group_forms_groups__group_id__delete","parameters":[{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"The group's id.","title":"Group Id"},"description":"The group's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"forms:delete","x-graph8-lifecycle":"active"}},"/forms/groups/{group_id}/members":{"post":{"tags":["Forms"],"summary":"Add Form Group Members","description":"Add inventory rows to a group. Existing members stay.","operationId":"add_form_group_members_forms_groups__group_id__members_post","parameters":[{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"The group's id.","title":"Group Id"},"description":"The group's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormGroupMembersRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"forms:write","x-graph8-lifecycle":"active"}},"/forms/groups/{group_id}/members/remove":{"post":{"tags":["Forms"],"summary":"Remove Form Group Members","description":"Remove inventory rows from a group.\n\nPOST rather than DELETE because it names a SET in a body, and enough\nproxies strip a DELETE body to make removal silently remove nothing.","operationId":"remove_form_group_members_forms_groups__group_id__members_remove_post","parameters":[{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"The group's id.","title":"Group Id"},"description":"The group's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormGroupMembersRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"forms:write","x-graph8-lifecycle":"active"}},"/forms/site-audit":{"get":{"tags":["Forms"],"summary":"Get Site Audit","description":"Findings from the last crawl: forms on the site that are not being captured.","operationId":"get_site_audit_forms_site_audit_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"forms:read","x-graph8-lifecycle":"active"}},"/forms/site-audit/scan":{"post":{"tags":["Forms"],"summary":"Request Site Audit Scan","description":"Crawl the site again. ASYNCHRONOUS; read `GET /forms/site-audit` afterwards.\n\nAt most one enqueue per org per minute: inside that window the answer is\n`already_queued` and nothing new is started.","operationId":"request_site_audit_scan_forms_site_audit_scan_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"forms:write","x-graph8-lifecycle":"active"}},"/forms/site-audit/findings/{finding_id}":{"patch":{"tags":["Forms"],"summary":"Update Site Audit Finding","description":"Triage one finding. `ignored` keeps it out of future reports without resolving it.","operationId":"update_site_audit_finding_forms_site_audit_findings__finding_id__patch","parameters":[{"name":"finding_id","in":"path","required":true,"schema":{"type":"string","description":"The finding's id.","title":"Finding Id"},"description":"The finding's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormSiteAuditStatusRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"forms:write","x-graph8-lifecycle":"active"}},"/forms/{form_key}/submissions":{"post":{"tags":["Forms"],"summary":"Search Form Submissions","description":"What people actually submitted to one form.\n\nA paginated READ; POST only because the filter set is a body. Identifying\nfields are REDACTED for a key without the Signals write capability, exactly\nas in the browser - an empty-looking value is a redaction, not a missing\nsubmission.","operationId":"search_form_submissions_forms__form_key__submissions_post","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"The form's `form_key` (the `id` from `GET /forms`).","title":"Form Key"},"description":"The form's `form_key` (the `id` from `GET /forms`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormSubmissionsSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"forms:read","x-graph8-lifecycle":"active"}},"/forms/{form_key}/mapping/preview":{"post":{"tags":["Forms"],"summary":"Preview Form Mapping","description":"What submissions would look like under a mapping, WITHOUT saving it.\n\nNothing is written and no list is filled. Same PII rule as the submissions read.","operationId":"preview_form_mapping_forms__form_key__mapping_preview_post","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"The form's `form_key` (the `id` from `GET /forms`).","title":"Form Key"},"description":"The form's `form_key` (the `id` from `GET /forms`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormMappingRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"forms:read","x-graph8-lifecycle":"active"}},"/forms/{form_key}/mapping/save":{"post":{"tags":["Forms"],"summary":"Save Form Mapping","description":"Save how a form's submitted fields become contact fields.\n\nA FULL REPLACEMENT of the mapping. Everything captured from now on lands\naccording to it, so preview first. `expected_route_version` makes it a\nconditional write (409 when someone else saved in between).","operationId":"save_form_mapping_forms__form_key__mapping_save_post","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"The form's `form_key` (the `id` from `GET /forms`).","title":"Form Key"},"description":"The form's `form_key` (the `id` from `GET /forms`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormMappingRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"forms:write","x-graph8-lifecycle":"active"}},"/forms/{form_key}/backfills":{"post":{"tags":["Forms"],"summary":"Create Form Backfill","description":"Deliver submissions captured in a window through the form's current route.\n\n`preview` DEFAULTS TO TRUE, and that default is the safety: a real backfill\ndelivers real leads to a real destination and there is no undo. Preview,\nread the count, then send `preview: false` with that count as `estimated`.","operationId":"create_form_backfill_forms__form_key__backfills_post","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"The form's `form_key` (the `id` from `GET /forms`).","title":"Form Key"},"description":"The form's `form_key` (the `id` from `GET /forms`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormBackfillRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"forms:run","x-graph8-lifecycle":"active"}},"/forms/{form_key}/backfills/{job_id}":{"get":{"tags":["Forms"],"summary":"Get Form Backfill","description":"How a backfill is going, and what it delivered.","operationId":"get_form_backfill_forms__form_key__backfills__job_id__get","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"The form's `form_key` (the `id` from `GET /forms`).","title":"Form Key"},"description":"The form's `form_key` (the `id` from `GET /forms`)."},{"name":"job_id","in":"path","required":true,"schema":{"type":"string","description":"Job id from the backfill that started it.","title":"Job Id"},"description":"Job id from the backfill that started it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"forms:read","x-graph8-lifecycle":"active"}},"/forms/{form_key}/preview":{"post":{"tags":["Forms"],"summary":"Capture Form Preview","description":"Queue a screenshot of this form on one page it was actually seen on.\n\nASYNCHRONOUS: poll `GET /forms/{form_key}/preview/{preview_id}`. A page the\nform was never observed on is a 404 - it captures real placements only.","operationId":"capture_form_preview_forms__form_key__preview_post","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"The form's `form_key` (the `id` from `GET /forms`).","title":"Form Key"},"description":"The form's `form_key` (the `id` from `GET /forms`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FormPlacementPreviewRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"forms:write","x-graph8-lifecycle":"active"}},"/forms/{form_key}/preview/{preview_id}":{"get":{"tags":["Forms"],"summary":"Get Form Preview","description":"One placement preview: its state and, once captured, where the image is.","operationId":"get_form_preview_forms__form_key__preview__preview_id__get","parameters":[{"name":"form_key","in":"path","required":true,"schema":{"type":"string","description":"The form's `form_key` (the `id` from `GET /forms`).","title":"Form Key"},"description":"The form's `form_key` (the `id` from `GET /forms`)."},{"name":"preview_id","in":"path","required":true,"schema":{"type":"string","description":"Id from the capture that started it.","title":"Preview Id"},"description":"Id from the capture that started it."},{"name":"source_id","in":"query","required":true,"schema":{"type":"string","description":"The site (write key) the form is installed on.","title":"Source Id"},"description":"The site (write key) the form is installed on."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_FormsAdminPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"forms:read","x-graph8-lifecycle":"active"}},"/public/copilot/chat":{"post":{"tags":["Public - Copilot"],"summary":"Public Copilot Chat","description":"Send a message to the graph8 copilot using write key auth.\n\nThis is a simplified, non-streaming version for the SDK widget.\nResponses come from the org's knowledge base (global context docs,\nbrand brief, FAQs, etc.) — no admin tools are available.\n\nUsed by g8.copilot.ask().","operationId":"public_copilot_chat_public_copilot_chat_post","parameters":[{"name":"X-Write-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Write-Key"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PublicCopilotRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PublicCopilotResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-lifecycle":"active"}},"/copilot/memory/context":{"get":{"tags":["Copilot"],"summary":"Get Copilot Memory Context","description":"The memory the Copilot would actually bring to a given conversation.\n\nNot the whole store - the ASSEMBLED context for a subject, which is what\nthe assistant reasons from. The most useful read here when debugging \"why\ndid it say that\": if a fact is not in this answer, it was not in front of\nthe model.\n\nWith no filters it returns the org and user level context alone.","operationId":"get_copilot_memory_context_copilot_memory_context_get","parameters":[{"name":"campaign_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to one campaign.","title":"Campaign Id"},"description":"Narrow to one campaign."},{"name":"company_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to one company.","title":"Company Id"},"description":"Narrow to one company."},{"name":"contact_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to one contact.","title":"Contact Id"},"description":"Narrow to one contact."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/copilot/memory/documents":{"get":{"tags":["Copilot"],"summary":"Get Copilot Memory Documents","description":"The raw memory documents for one subject.\n\n`soul` is who they are, `memory` is durable fact, `daily` is the rolling\njournal. `GET /copilot/memory/context` is the assembled view; this is the\nsource behind it, and the thing to edit.","operationId":"get_copilot_memory_documents_copilot_memory_documents_get","parameters":[{"name":"subject_type","in":"query","required":true,"schema":{"type":"string","description":"organization | user | campaign | company | contact.","title":"Subject Type"},"description":"organization | user | campaign | company | contact."},{"name":"subject_id","in":"query","required":true,"schema":{"type":"string","description":"Which one.","title":"Subject Id"},"description":"Which one."},{"name":"file_kind","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"`soul`, `memory` or `daily`. Omit for all three - they are different documents, not versions of one.","title":"File Kind"},"description":"`soul`, `memory` or `daily`. Omit for all three - they are different documents, not versions of one."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"},"put":{"tags":["Copilot"],"summary":"Upsert Copilot Memory Document","description":"Write a memory document WHOLE. This replaces, it does not merge.\n\n`visibility` defaults to `shared`, which means the whole organisation's\nCopilot may draw on it. That is the app's default and it is the wider of\nthe two, so it is what you get by not thinking about it - worth thinking\nabout it.","operationId":"upsert_copilot_memory_document_copilot_memory_documents_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MemoryDocumentRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/copilot/memory/documents/append":{"post":{"tags":["Copilot"],"summary":"Append Copilot Memory Document","description":"Add to a memory document without replacing it.\n\nDefaults to the `daily` journal, which is where observations belong: the\ndurable documents are meant to be curated from it by\n`POST /copilot/memory/promote`, not written to directly on every event.\n\nTakes a JSON BODY. The app takes these as query parameters, which would put\nthe text of a personal note into the URL.","operationId":"append_copilot_memory_document_copilot_memory_documents_append_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MemoryDocumentAppendRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/copilot/memory/promote":{"post":{"tags":["Copilot"],"summary":"Promote Copilot Memory","description":"Promote what is worth keeping out of the daily journal into durable\nmemory.\n\nThe garbage-collection step of the whole memory design. Without it the\njournal grows without bound and the durable documents stay empty, so the\nassistant ends up with a great deal of noise and very little knowledge.","operationId":"promote_copilot_memory_copilot_memory_promote_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PromoteMemoryRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"knowledge:run","x-graph8-lifecycle":"active"}},"/copilot/memory/soul-capture":{"post":{"tags":["Copilot"],"summary":"Capture Copilot Soul","description":"Set the organisation's and the user's foundational documents in one call.\n\nThe onboarding shortcut: it is how a new workspace tells the assistant who\nit works for before there is any history to learn from. Every field is\noptional and sending one does not clear the others.","operationId":"capture_copilot_soul_copilot_memory_soul_capture_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SoulCaptureRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/copilot/memory":{"get":{"tags":["Copilot"],"summary":"List Copilot Memories","description":"Discrete things the Copilot has been told to remember.\n\nNOT the same store as `GET /agent/memory`, which is the agent runtime's\nplanner state. These are the assistant's own remembered facts.","operationId":"list_copilot_memories_copilot_memory_get","parameters":[{"name":"scope","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter to one memory scope.","title":"Scope"},"description":"Filter to one memory scope."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Page size.","default":20,"title":"Limit"},"description":"Page size."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"},"post":{"tags":["Copilot"],"summary":"Create Copilot Memory","description":"Tell the Copilot something to remember.\n\nTakes a JSON BODY. The app takes `content` as a query parameter, which puts\nthe text of a personal memory into the URL and therefore into access logs.","operationId":"create_copilot_memory_copilot_memory_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MemoryCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/copilot/memory/{memory_id}":{"delete":{"tags":["Copilot"],"summary":"Delete Copilot Memory","description":"Forget one remembered fact. Not reversible.","operationId":"delete_copilot_memory_copilot_memory__memory_id__delete","parameters":[{"name":"memory_id","in":"path","required":true,"schema":{"type":"string","description":"Memory id.","title":"Memory Id"},"description":"Memory id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"knowledge:delete","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki":{"get":{"tags":["Copilot"],"summary":"Get Copilot Personal Wiki","description":"Everything the assistant believes about the person behind this key.\n\nAssembled from their email, calendar, documents and Work activity according\nto `GET /copilot/personal-wiki/sources`. Each fact carries where it came\nfrom, which is what makes a wrong one correctable rather than merely\nannoying.","operationId":"get_copilot_personal_wiki_copilot_personal_wiki_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"},"put":{"tags":["Copilot"],"summary":"Update Copilot Personal Wiki","description":"Replace the wiki document WHOLE.\n\nThe blunt instrument. Prefer `confirm`, `correct` and `forget`, which act on\nONE fact and leave its provenance intact - this replaces the document and\nthe Copilot then has to re-derive what it knew.","operationId":"update_copilot_personal_wiki_copilot_personal_wiki_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonalWikiUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/sources":{"get":{"tags":["Copilot"],"summary":"Get Copilot Personal Wiki Sources","description":"Which of your things the assistant is reading.\n\nMailboxes, calendar, documents, Work. The privacy answer for this whole\nsurface - what the wiki knows follows directly from what is switched on\nhere.","operationId":"get_copilot_personal_wiki_sources_copilot_personal_wiki_sources_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"},"put":{"tags":["Copilot"],"summary":"Update Copilot Personal Wiki Sources","description":"Change what the assistant may read.\n\nPARTIAL: an omitted field is left alone, an explicit one changes it. So\nomitting `email_enabled` and sending `false` are different instructions.\n\nSWITCHING A SOURCE OFF DOES NOT UNLEARN. It stops new facts arriving from\nthere; what was already derived stays until it is forgotten one fact at a\ntime through `POST /copilot/personal-wiki/forget`.","operationId":"update_copilot_personal_wiki_sources_copilot_personal_wiki_sources_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonalWikiSourcesUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/documents/{section}":{"get":{"tags":["Copilot"],"summary":"Get Copilot Personal Wiki Document","description":"One source document behind a section of the wiki.\n\nThe evidence view: the actual text a section was derived from, rather than\nthe assistant's summary of it.","operationId":"get_copilot_personal_wiki_document_copilot_personal_wiki_documents__section__get","parameters":[{"name":"section","in":"path","required":true,"schema":{"type":"string","description":"Wiki section.","title":"Section"},"description":"Wiki section."},{"name":"document_id","in":"query","required":true,"schema":{"type":"string","description":"Which source document.","title":"Document Id"},"description":"Which source document."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/items/{item_id}":{"put":{"tags":["Copilot"],"summary":"Edit Copilot Personal Wiki Item","description":"Edit one structured item in the wiki.\n\n`expected_revision` is REQUIRED and there is no unconditional form. The\nCopilot writes this document continuously, so an unguarded write is not a\nrace between two people - it is a person silently discarding whatever the\nassistant learned between their read and their write.","operationId":"edit_copilot_personal_wiki_item_copilot_personal_wiki_items__item_id__put","parameters":[{"name":"item_id","in":"path","required":true,"schema":{"type":"string","description":"Wiki item id.","title":"Item Id"},"description":"Wiki item id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonalWikiItemEditRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/confirm":{"post":{"tags":["Copilot"],"summary":"Confirm Copilot Personal Wiki Fact","description":"Tell the assistant an inferred fact is RIGHT.\n\nWorth doing rather than ignoring: a confirmed fact stops being re-derived\nand re-questioned, and it outranks a later contradicting inference.","operationId":"confirm_copilot_personal_wiki_fact_copilot_personal_wiki_confirm_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonalWikiFactActionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/correct":{"post":{"tags":["Copilot"],"summary":"Correct Copilot Personal Wiki Fact","description":"Replace what the assistant believes with what is actually true.\n\nDifferent from `forget`: correcting keeps the fact and its provenance and\nchanges its text, so the assistant knows it was wrong about THIS rather\nthan knowing nothing.","operationId":"correct_copilot_personal_wiki_fact_copilot_personal_wiki_correct_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonalWikiFactCorrectionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/forget":{"post":{"tags":["Copilot"],"summary":"Forget Copilot Personal Wiki Fact","description":"Remove a fact from what the assistant knows.\n\nThe per-fact privacy control, and the only one that actually unlearns -\nturning a SOURCE off stops new facts arriving but leaves the old ones.\n\nSend `reason`. It is the only record of why something was removed.","operationId":"forget_copilot_personal_wiki_fact_copilot_personal_wiki_forget_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonalWikiFactActionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/relationships":{"get":{"tags":["Copilot"],"summary":"List Copilot Personal Wiki Relationships","description":"Who the assistant thinks you know, and how well.\n\nFiltered by the key's CONTACT SCOPE, not just by org: a key whose user may\nonly see their own contacts sees relationships to those contacts. The\nrelationship graph is derived from a person's mailbox, so it is exactly the\ndata that must not cross a rep boundary.","operationId":"list_copilot_personal_wiki_relationships_copilot_personal_wiki_relationships_get","parameters":[{"name":"item_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","minLength":1,"maxLength":100},{"type":"null"}],"title":"Item Id"}},{"name":"query","in":"query","required":false,"schema":{"type":"string","maxLength":120,"description":"Substring match on the person.","default":"","title":"Query"},"description":"Substring match on the person."},{"name":"sort","in":"query","required":false,"schema":{"enum":["recent","name","email"],"type":"string","description":"`recent`, `name` or `email`.","default":"recent","title":"Sort"},"description":"`recent`, `name` or `email`."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/contact-identities":{"get":{"tags":["Copilot"],"summary":"Search Copilot Contact Identities","description":"Find the CRM contact a wiki fact is really about.\n\nThe lookup behind `POST /copilot/personal-wiki/relationships/identity`. The\ntwo-character minimum is the app's and is real: it is a scoped search over\npeople, not a prefix index.","operationId":"search_copilot_contact_identities_copilot_personal_wiki_contact_identities_get","parameters":[{"name":"query","in":"query","required":true,"schema":{"type":"string","minLength":2,"maxLength":120,"description":"At least two characters.","title":"Query"},"description":"At least two characters."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/relationships/identity":{"post":{"tags":["Copilot"],"summary":"Correct Copilot Contact Identity","description":"Re-attribute facts to the right person - or to nobody.\n\nSending a null `contact_id` DETACHES the facts rather than being ignored:\nit is how you say \"this is not about anyone in the CRM\". Up to a thousand\nfacts move at once, because a misattribution is usually systematic rather\nthan a single fact.\n\nDeclared BEFORE `/personal-wiki/relationships/{contact_id}` so the literal\n`identity` segment cannot be captured as a contact id.","operationId":"correct_copilot_contact_identity_copilot_personal_wiki_relationships_identity_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonalContactIdentityRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/relationships/{contact_id}":{"get":{"tags":["Copilot"],"summary":"Get Copilot Personal Wiki Relationship","description":"What the assistant knows about your relationship with ONE person.","operationId":"get_copilot_personal_wiki_relationship_copilot_personal_wiki_relationships__contact_id__get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"CRM contact id (integer).","title":"Contact Id"},"description":"CRM contact id (integer)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/contact-sharing/contributions":{"get":{"tags":["Copilot"],"summary":"List Copilot Contact Contributions","description":"What your mailbox is offering to the shared CRM record, pending review.\n\nA contribution is a fact the assistant learned privately that WOULD change\na shared contact - a new job title, a corrected name. It is held here until\nsomeone decides, rather than being written straight through.","operationId":"list_copilot_contact_contributions_copilot_personal_wiki_contact_sharing_contributions_get","parameters":[{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"default":25,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/contact-sharing/contributions/{contribution_id}":{"put":{"tags":["Copilot"],"summary":"Update Copilot Contact Contribution","description":"Turn ONE contribution on or off.\n\n`expected_revision` is required. This decides whether private knowledge\nbecomes org-wide, so a blind write could re-enable sharing somebody had\njust switched off.","operationId":"update_copilot_contact_contribution_copilot_personal_wiki_contact_sharing_contributions__contribution_id__put","parameters":[{"name":"contribution_id","in":"path","required":true,"schema":{"type":"string","description":"Contribution id (UUID).","title":"Contribution Id"},"description":"Contribution id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonalContactSharingRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/contact-sharing/contributions/{contribution_id}/resolve":{"post":{"tags":["Copilot"],"summary":"Resolve Copilot Contact Contribution","description":"Decide ONE FIELD of a contribution: keep the CRM value, or take the\nproposed one.\n\nPer field rather than per contribution, because a contribution can be right\nabout a job title and wrong about a surname.\n\nTWO concurrency tokens are required and both are load-bearing: one for the\ncontribution and one for the CANONICAL contact record the decision would\nchange. Either having moved means the decision was made against something\nthat no longer holds, and `use_proposed` OVERWRITES a shared record.","operationId":"resolve_copilot_contact_contribution_copilot_personal_wiki_contact_sharing_contributions__contribution_id__resolve_post","parameters":[{"name":"contribution_id","in":"path","required":true,"schema":{"type":"string","description":"Contribution id (UUID).","title":"Contribution Id"},"description":"Contribution id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonalContactReviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/contact-sharing/contributions/{contribution_id}/matches":{"get":{"tags":["Copilot"],"summary":"List Copilot Contact Matches","description":"Which CRM contacts this contribution might be about.\n\nRead this before resolving one. A contribution that matches several people\nis a contribution whose decision would otherwise land on whichever the\nmatcher guessed.","operationId":"list_copilot_contact_matches_copilot_personal_wiki_contact_sharing_contributions__contribution_id__matches_get","parameters":[{"name":"contribution_id","in":"path","required":true,"schema":{"type":"string","description":"Contribution id (UUID).","title":"Contribution Id"},"description":"Contribution id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"},"post":{"tags":["Copilot"],"summary":"Choose Copilot Contact Match","description":"Say WHICH person a contribution is about.\n\nBinds it to one CRM contact, so the subsequent per-field decisions land on\nthe right record. Guarded by both revision tokens for the same reason the\nresolve is.","operationId":"choose_copilot_contact_match_copilot_personal_wiki_contact_sharing_contributions__contribution_id__matches_post","parameters":[{"name":"contribution_id","in":"path","required":true,"schema":{"type":"string","description":"Contribution id (UUID).","title":"Contribution Id"},"description":"Contribution id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonalContactMatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/contact-sharing":{"get":{"tags":["Copilot"],"summary":"Get Copilot Contact Sharing","description":"Which of your mailboxes contribute to the shared CRM, per mailbox.\n\nThe setting; `/contributions` is the queue it produces.","operationId":"get_copilot_contact_sharing_copilot_personal_wiki_contact_sharing_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/contact-sharing/{mailbox_id}":{"put":{"tags":["Copilot"],"summary":"Update Copilot Contact Sharing","description":"Turn contact sharing on or off for ONE mailbox.\n\nThe switch that decides whether a person's private contact knowledge starts\nproducing contributions at all. `expected_revision` is required.","operationId":"update_copilot_contact_sharing_copilot_personal_wiki_contact_sharing__mailbox_id__put","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","description":"Integer `mailboxes.id` - the database primary key, not the cron-job string id.","title":"Mailbox Id"},"description":"Integer `mailboxes.id` - the database primary key, not the cron-job string id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonalContactSharingRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/drive":{"get":{"tags":["Copilot"],"summary":"Browse Copilot Personal Wiki Drive","description":"Browse the Google Drive of one of your connected mailboxes, to pick what\nthe Copilot may read.\n\nReads Drive through the mailbox's own grant. A 403 means the grant does\nnot include Drive; a 409 means the Google account behind the mailbox has\nchanged since it was connected.","operationId":"browse_copilot_personal_wiki_drive_copilot_personal_wiki_drive_get","parameters":[{"name":"mailbox_id","in":"query","required":true,"schema":{"type":"integer","exclusiveMinimum":0,"description":"Integer `mailboxes.id` of the connected Google account.","title":"Mailbox Id"},"description":"Integer `mailboxes.id` of the connected Google account."},{"name":"parent_id","in":"query","required":false,"schema":{"type":"string","minLength":1,"maxLength":200,"pattern":"^[A-Za-z0-9_-]+$","description":"Folder to list. `root` is the top of My Drive.","default":"root","title":"Parent Id"},"description":"Folder to list. `root` is the top of My Drive."},{"name":"page_token","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"description":"From the previous page.","title":"Page Token"},"description":"From the previous page."},{"name":"search","in":"query","required":false,"schema":{"type":"string","maxLength":120,"description":"Search by name instead of listing a folder.","default":"","title":"Search"},"description":"Search by name instead of listing a folder."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/drive-selection/preview":{"post":{"tags":["Copilot"],"summary":"Preview Copilot Personal Wiki Drive Selection","description":"What a Drive selection WOULD read, without saving it.\n\nPOST only because the selection is a body; it changes nothing. Returns a\n`fingerprint` to hand to the save, so the save is refused if the folders\nhave changed underneath you in between.","operationId":"preview_copilot_personal_wiki_drive_selection_copilot_personal_wiki_drive_selection_preview_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonalDriveSelectionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/drive-selection":{"put":{"tags":["Copilot"],"summary":"Save Copilot Personal Wiki Drive Selection","description":"Save which Drive documents and folders the Copilot may read.\n\nReplaces the Drive part of the selection. `revision` is required in\npractice: it must equal the sources' current `updated_at`, or the save is\na 409.","operationId":"save_copilot_personal_wiki_drive_selection_copilot_personal_wiki_drive_selection_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonalDriveSelectionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/linkedin-connections":{"get":{"tags":["Copilot"],"summary":"Get Copilot Linkedin Connections","description":"The state of your LinkedIn connections import: settings, last run and\nits `revision` token.","operationId":"get_copilot_linkedin_connections_copilot_personal_wiki_linkedin_connections_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"},"put":{"tags":["Copilot"],"summary":"Update Copilot Linkedin Connections","description":"Change the LinkedIn connections import settings, and optionally start\nan import (`start: true`).\n\nThe import itself runs in the background; read its progress back with the\nGET. `expected_revision` is required.","operationId":"update_copilot_linkedin_connections_copilot_personal_wiki_linkedin_connections_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonalLinkedInImportRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/copilot/personal-wiki/contact-sharing/people/choice":{"put":{"tags":["Copilot"],"summary":"Update Copilot Contact People Choice","description":"Keep specific people private, share them, or let them follow the\nmailbox default.\n\nThe per-person override on top of `PUT /copilot/personal-wiki/contact-sharing/{mailbox_id}`.\n`expected_revision` is required.","operationId":"update_copilot_contact_people_choice_copilot_personal_wiki_contact_sharing_people_choice_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonalContactChoiceRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CopilotMemoryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/campaigns/ideas":{"get":{"tags":["GTM Campaigns"],"summary":"List Campaign Ideas","description":"List saved campaign ideas for this organization.","operationId":"list_campaign_ideas_campaigns_ideas_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page","default":50,"title":"Limit"},"description":"Items per page"},{"name":"favorited","in":"query","required":false,"schema":{"anyOf":[{"type":"boolean"},{"type":"null"}],"description":"Filter favorited ideas","title":"Favorited"},"description":"Filter favorited ideas"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/campaigns":{"get":{"tags":["GTM Campaigns"],"summary":"List Campaigns","description":"List campaigns for this organization.","operationId":"list_campaigns_campaigns_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number","default":1,"title":"Page"},"description":"Page number"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page","default":50,"title":"Limit"},"description":"Items per page"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"post":{"tags":["GTM Campaigns"],"summary":"Create Campaign","description":"Create a new campaign from scratch — full Studio \"Convert to Campaign\" parity.\n\nThe original handler only inserted ``cb_campaigns``. That left two\nStudio-side gaps:\n\n1. Studio's Campaigns workbench (``frontend/features/studio/components/\n   CampaignUnifiedTable.tsx``) filters ``cb_campaign_ideas`` WHERE\n   ``converted_to_campaign=true`` and joins back to ``cb_campaigns`` via\n   ``converted_campaign_id``. With no paired idea row, MCP-created\n   campaigns were invisible in the workbench (only the direct\n   ``/studio?campaignId=...`` URL worked).\n2. No documents were generated, so the campaign sat in \"Not Ready\" state\n   indefinitely. The launch flow silently produced empty sequences.\n\nThis handler now mirrors ``campaign_builder/routers/campaign_conversion.py\n:convert_idea_to_campaign`` end-to-end:\n\n* INSERT cb_campaigns (status=``copy_in_progress`` when generating, else ``draft``)\n* INSERT paired cb_campaign_ideas row with ``source='mcp'``,\n  ``converted_to_campaign=true``, ``converted_campaign_id=<new>``\n* INSERT cb_campaign_metadata with ``total_documents`` calculated from the\n  target channels\n* Scaffold ``sequence`` + ``step_catalog`` stub docs (idempotent)\n* Dispatch ``generate_campaign_files_from_idea.delay(...)`` to Celery\n\nBackwards-compatible: original 7-field callers still work AND see\nbyte-for-byte identical behavior because ``auto_generate_documents``\ndefaults to ``False``. All Studio-parity behavior (paired idea row,\nmetadata row, Celery dispatch, status='copy_in_progress') is opt-in\nvia ``auto_generate_documents=True``. The MCP ``g8_gtm_create_campaign``\ntool wrapper sets it to ``True`` so Daniel's GTM agent gets the fix\nwithout affecting any other direct API caller.","operationId":"create_campaign_campaigns_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/developer_api__interfaces__v1__gtm_campaigns_router__CampaignCreateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/documents":{"get":{"tags":["GTM Campaigns"],"summary":"List Campaign Documents","description":"List document metadata for a campaign.","operationId":"list_campaign_documents_campaigns__campaign_id__documents_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"post":{"tags":["GTM Campaigns"],"summary":"Create Campaign Document","description":"Create a campaign document with content stored in metadata.\n\n``meta_data`` shape mirrors what the Celery doc-generator writes so the\nFE renders MCP-created docs identically: ``content`` (markdown body),\n``completed`` (mirrors status=='completed' so launch checklist counts\nit), and optional ``structured_data`` (parsed payload, e.g. sequence\nstep list).","operationId":"create_campaign_document_campaigns__campaign_id__documents_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CampaignDocumentCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/documents/{document_id}":{"get":{"tags":["GTM Campaigns"],"summary":"Get Campaign Document","description":"Get full content of a specific campaign document.","operationId":"get_campaign_document_campaigns__campaign_id__documents__document_id__get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document ID","title":"Document Id"},"description":"Document ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"put":{"tags":["GTM Campaigns"],"summary":"Update Campaign Document","description":"Update campaign document content and optional structured data.","operationId":"update_campaign_document_campaigns__campaign_id__documents__document_id__put","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document ID","title":"Document Id"},"description":"Document ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CampaignDocumentUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"},"delete":{"tags":["GTM Campaigns"],"summary":"Delete Campaign Document","description":"Delete a campaign document.","operationId":"delete_campaign_document_campaigns__campaign_id__documents__document_id__delete","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"document_id","in":"path","required":true,"schema":{"type":"string","description":"Document ID","title":"Document Id"},"description":"Document ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/ad-images":{"get":{"tags":["GTM Campaigns"],"summary":"List Campaign Ad Images","description":"List ad image creatives generated for this campaign.\n\nAd images live in `cb_website_images` with `category='ad'` and a\n`campaign_id` back-reference (the AI generator writes there, NOT into\n`cb_campaign_documents`). This endpoint gives the MCP HTML resource a\nsingle place to pull the creative grid without reaching into the\nStudio-private `/v1/website-images` path.","operationId":"list_campaign_ad_images_campaigns__campaign_id__ad_images_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/ad-images/{image_id}/hide":{"post":{"tags":["GTM Campaigns"],"summary":"Hide Campaign Ad Image","description":"Mark an ad image as hidden (feedback='down'), so it drops out of the\nMCP App grid and any future listing.\n\nIdempotent: re-posting against an already-hidden image is a no-op, still\nreturns 200. Returns 404 only if the image doesn't exist (or doesn't\nbelong to the caller's org / this campaign).\n\nThis is the interactive action on the `ui://campaigns/ad-images` MCP\nApp. The app calls `g8_hide_ad_image` over postMessage; that tool hits\nthis endpoint; the response tells the app which image id to drop from\nits local state.","operationId":"hide_campaign_ad_image_campaigns__campaign_id__ad_images__image_id__hide_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"image_id","in":"path","required":true,"schema":{"type":"string","description":"Ad image ID (cb_website_images.id)","title":"Image Id"},"description":"Ad image ID (cb_website_images.id)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/sequence":{"get":{"tags":["GTM Campaigns"],"summary":"Get Campaign Sequence","description":"Get the campaign sequence and step catalog documents.","operationId":"get_campaign_sequence_campaigns__campaign_id__sequence_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"put":{"tags":["GTM Campaigns"],"summary":"Update Campaign Sequence","description":"Replace the campaign sequence ordering.","operationId":"update_campaign_sequence_campaigns__campaign_id__sequence_put","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/developer_api__interfaces__v1__gtm_campaigns_router__UpdateSequenceRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/sequence/steps":{"post":{"tags":["GTM Campaigns"],"summary":"Create Campaign Step","description":"Create a step definition and append it to the campaign sequence.","operationId":"create_campaign_step_campaigns__campaign_id__sequence_steps_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateStepRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/sequence/steps/{step_id}":{"put":{"tags":["GTM Campaigns"],"summary":"Update Campaign Step","description":"Update a sequence step definition and optional placement metadata.","operationId":"update_campaign_step_campaigns__campaign_id__sequence_steps__step_id__put","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"step_id","in":"path","required":true,"schema":{"type":"string","description":"Step ID","title":"Step Id"},"description":"Step ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateStepRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"},"delete":{"tags":["GTM Campaigns"],"summary":"Delete Campaign Step","description":"Remove a sequence step from the catalog and sequence order.","operationId":"delete_campaign_step_campaigns__campaign_id__sequence_steps__step_id__delete","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"step_id","in":"path","required":true,"schema":{"type":"string","description":"Step ID","title":"Step Id"},"description":"Step ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/launch":{"post":{"tags":["GTM Campaigns"],"summary":"Launch Campaign","description":"Launch a campaign through the canonical Sequencer V2 workflow.\n\nThis does two things end-to-end:\n\n1. **Push** the campaign to the sequencer. The bridge loads the campaign's\n   generated documents (email/LinkedIn/phone/SMS copy), transforms them\n   into sequencer steps, and creates a new ``SeqSequence`` row with the\n   campaign content attached. A ``CampaignSequenceLink`` row links the two.\n2. **Run** the sequence through the same V2 workflow used by Sequencer.\n   The response reports ``live`` only after synchronous initialization has\n   completed, or ``scheduling`` with job details for background work.\n\nIdempotency: re-launching a campaign that already has an active sequence\nreturns 409 unless ``force`` is implied via a future query-param. This is\nconsistent with the UI's bridge/push behaviour.\n\nPre-flight is mandatory. The deprecated ``validate`` parameter is accepted\nonly as ``true``; ``false`` is rejected before any sequence is created.\n\nWARNING: this begins sending real outreach to real contacts.","operationId":"launch_campaign_campaigns__campaign_id__launch_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"validate","in":"query","required":false,"schema":{"type":"boolean","description":"Deprecated compatibility parameter. Readiness validation is always enforced; false is rejected before any sequence is created.","deprecated":true,"default":true,"title":"Validate"},"description":"Deprecated compatibility parameter. Readiness validation is always enforced; false is rejected before any sequence is created.","deprecated":true},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/CampaignLaunchRequest"},{"type":"null"}],"title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:launch","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/audience":{"put":{"tags":["GTM Campaigns"],"summary":"Attach Audience To Campaign","description":"Attach (or detach) a saved list to a campaign as its audience.\n\nThis is the missing link in Daniel's MCP flow: ``find list → create\ncampaign → attach audience → launch`` was previously a dead-end because\nno REST/MCP path could set ``cb_campaigns.audience_list_id`` (the FE\n\"Attach Audience\" dialog only went through an internal route).\n\nIdempotent — setting the same list twice is a 200, no error. Pass\n``list_id=null`` to detach. The launch endpoint reads\n``cb_campaigns.audience_list_id`` when enrolling contacts; without it,\nlaunch creates a sequence with zero enrollment.","operationId":"attach_audience_to_campaign_campaigns__campaign_id__audience_put","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CampaignAttachAudienceRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/metrics":{"get":{"tags":["GTM Campaigns"],"summary":"Get Campaign Metrics","description":"Get campaign execution metrics — sequence status + email sent/replied counts.\n\nThin wrapper around the existing ``campaigns.metrics`` handler. The\nhandler queries ClickHouse for per-sequence event aggregates and joins\nthem to the campaign's linked sequences via ``cb_campaign_sequence_links``.\n\nRead-only. Returns the same shape the handler produces. Each campaign carries\na ``metric_status`` (available | zero | stale | unknown | missing) that\nreconciles the ClickHouse engagement rollup against Postgres send receipts\n(``seqcontactexecutedsteps``): if analytics are unreachable the status is\n``unknown`` (NOT a zero), and if send receipts prove sends the rollup has not\ncounted the status is ``stale``. Read ``reconciliation`` and ``measured_range``\nbefore concluding anything about delivery — never treat a bare zero as an outage.","operationId":"get_campaign_metrics_campaigns__campaign_id__metrics_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Lookback window in days","default":30,"title":"Days"},"description":"Lookback window in days"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/full":{"get":{"tags":["GTM Campaigns"],"summary":"Get Campaign Full","description":"Get the **kitchen-sink** campaign payload in one round trip.\n\nIncludes: campaign row, attached audience list summary, ALL documents\n(with content), sequence + step catalog, and linked sequencer sequences\n(so the caller can tell at a glance whether the campaign has been\nlaunched yet).\n\nDesigned for the MCP \"load entire campaign for editing\" path so agents\ndon't have to chain ``GET /campaigns/{id}`` → ``/documents`` → ``/sequence``\njust to see the current state.","operationId":"get_campaign_full_campaigns__campaign_id__full_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["GTM Campaigns"],"summary":"Patch Campaign Full","description":"Apply a deep-update to a campaign in one round trip.\n\nBehavior:\n    - Campaign fields (name/brief/hook/etc.) update the row when present.\n    - ``audience_list_id`` attaches; ``detach_audience=true`` clears it.\n    - ``documents[*]`` either updates an existing doc by id, or creates a\n      new doc when id is omitted (file_type + display_name required).\n    - ``sequence_steps`` replaces the sequence ordering verbatim\n      (same semantics as PUT /sequence).\n\nReturns the full kitchen-sink payload (same shape as GET /full).\nBackwards-compat: omitting any field is a no-op. Existing single-purpose\nendpoints (PATCH /campaigns/{id}, PUT /audience, PUT /sequence, etc.)\nkeep working unchanged.","operationId":"patch_campaign_full_campaigns__campaign_id__full_patch","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign ID","title":"Campaign Id"},"description":"Campaign ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CampaignFullPatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/social/autopilot/{account_id}":{"get":{"tags":["Social Publishing"],"summary":"Get Social Autopilot","description":"Autopilot configuration for one account, including a disconnected one (so the reconnect state is visible).","operationId":"get_social_autopilot_social_autopilot__account_id__get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"An `id` from `GET /social/accounts`.","title":"Account Id"},"description":"An `id` from `GET /social/accounts`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialAutopilot_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"put":{"tags":["Social Publishing"],"summary":"Save Social Autopilot","description":"Configure autopilot for one account.\n\nWith `enabled` and `auto_publish_confirmed` both true, autopilot writes AND\nPUBLISHES posts on its own. Requires the campaign-launch permission, as in\nthe app.","operationId":"save_social_autopilot_social_autopilot__account_id__put","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"An `id` from `GET /social/accounts`.","title":"Account Id"},"description":"An `id` from `GET /social/accounts`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SocialAutopilotSaveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialAutopilot_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/social/autopilot/{account_id}/pause":{"post":{"tags":["Social Publishing"],"summary":"Pause Social Autopilot","description":"Stop autopilot for one account. Posts it already scheduled stay scheduled.","operationId":"pause_social_autopilot_social_autopilot__account_id__pause_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"An `id` from `GET /social/accounts`.","title":"Account Id"},"description":"An `id` from `GET /social/accounts`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialAutopilot_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/social/posts":{"post":{"tags":["Social Publishing"],"summary":"Create Social Post","description":"Create a DRAFT post. Nothing is published until you schedule or publish it.","operationId":"create_social_post_social_posts_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SocialPostCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPost_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"get":{"tags":["Social Publishing"],"summary":"List Social Posts","description":"Posts, newest first, with the org-wide count per status.","operationId":"list_social_posts_social_posts_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"enum":["draft","ready","scheduled","publishing","live","failed","cancelled"],"type":"string"},{"type":"null"}],"description":"Only posts in this state.","title":"Status"},"description":"Only posts in this state."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":25,"title":"Page Size"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPostPage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/social/posts/generate":{"post":{"tags":["Social Publishing"],"summary":"Generate Social Post","description":"Draft up to three variants with AI. SPENDS CREDITS (`credits_used`); saves nothing.","operationId":"generate_social_post_social_posts_generate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SocialPostGenerateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialGenerated_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/social/generate/context":{"get":{"tags":["Social Publishing"],"summary":"Get Social Generation Context","description":"Which grounding sources have data for AI drafting.","operationId":"get_social_generation_context_social_generate_context_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialGenerationContext_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/social/ideas":{"get":{"tags":["Social Publishing"],"summary":"List Social Ideas","description":"Post ideas mined from the org's own signals and content.","operationId":"list_social_ideas_social_ideas_get","parameters":[{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"enum":["signal_mining","linkedin_trending","proof_freshness","repurpose","ai"],"type":"string"},{"type":"null"}],"description":"Only ideas from this source.","title":"Source"},"description":"Only ideas from this source."},{"name":"refresh","in":"query","required":false,"schema":{"type":"boolean","description":"Mine fresh ideas before answering.","default":false,"title":"Refresh"},"description":"Mine fresh ideas before answering."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialIdeas_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/social/posts/{post_id}":{"get":{"tags":["Social Publishing"],"summary":"Get Social Post","description":"One post.","operationId":"get_social_post_social_posts__post_id__get","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"The post's id.","title":"Post Id"},"description":"The post's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPost_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Social Publishing"],"summary":"Update Social Post","description":"Edit a post that has not gone out yet. Only the fields you send change.","operationId":"update_social_post_social_posts__post_id__patch","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"The post's id.","title":"Post Id"},"description":"The post's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SocialPostUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPost_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Social Publishing"],"summary":"Delete Social Post","description":"Delete a post that has not been published. A published post is not removed from the network.","operationId":"delete_social_post_social_posts__post_id__delete","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"The post's id.","title":"Post Id"},"description":"The post's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialDeleted_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/social/posts/{post_id}/schedule":{"post":{"tags":["Social Publishing"],"summary":"Schedule Social Post","description":"Schedule a post. It PUBLISHES PUBLICLY at `scheduled_at` with no further step.","operationId":"schedule_social_post_social_posts__post_id__schedule_post","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"The post's id.","title":"Post Id"},"description":"The post's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SocialPostScheduleRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPost_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/social/posts/{post_id}/publish":{"post":{"tags":["Social Publishing"],"summary":"Publish Social Post","description":"Publish now. PUBLIC AND IRREVERSIBLE from here: the post goes out on the connected account.","operationId":"publish_social_post_social_posts__post_id__publish_post","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"The post's id.","title":"Post Id"},"description":"The post's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPublishAccepted_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/social/posts/{post_id}/cancel":{"post":{"tags":["Social Publishing"],"summary":"Cancel Social Post","description":"Take a scheduled post off the schedule. It stays as a post; nothing is published.","operationId":"cancel_social_post_social_posts__post_id__cancel_post","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"The post's id.","title":"Post Id"},"description":"The post's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPost_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/social/posts/{post_id}/metrics":{"get":{"tags":["Social Publishing"],"summary":"Get Social Post Metrics","description":"Impressions, reactions, comments and shares from the latest snapshot.","operationId":"get_social_post_metrics_social_posts__post_id__metrics_get","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"The post's id.","title":"Post Id"},"description":"The post's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPostMetrics_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/social/posts/{post_id}/engagers":{"get":{"tags":["Social Publishing"],"summary":"List Social Post Engagers","description":"People who reacted to or commented on a post, matched to contacts where possible.","operationId":"list_social_post_engagers_social_posts__post_id__engagers_get","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"The post's id.","title":"Post Id"},"description":"The post's id."},{"name":"refresh","in":"query","required":false,"schema":{"type":"boolean","description":"Fetch fresh from the network instead of the stored copy.","default":false,"title":"Refresh"},"description":"Fetch fresh from the network instead of the stored copy."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialEngagers_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/social/posts/{post_id}/engagers/add-to-audience":{"post":{"tags":["Social Publishing"],"summary":"Add Social Engagers To Audience","description":"Build an audience from a post's engagers, creating contacts for the ones not yet in the CRM.","operationId":"add_social_engagers_to_audience_social_posts__post_id__engagers_add_to_audience_post","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"The post's id.","title":"Post Id"},"description":"The post's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SocialAudienceFromEngagersRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialAudienceFromEngagers_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/social/posts/{post_id}/engagers/enroll":{"post":{"tags":["Social Publishing"],"summary":"Enroll Social Engagers","description":"Enroll engagers into a sequence. REAL OUTREACH: the sequence starts contacting them.","operationId":"enroll_social_engagers_social_posts__post_id__engagers_enroll_post","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"The post's id.","title":"Post Id"},"description":"The post's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SocialEnrollEngagersRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialEnrollResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/social/analytics":{"get":{"tags":["Social Publishing"],"summary":"Get Social Analytics","description":"Totals and a per-day series across all posts.","operationId":"get_social_analytics_social_analytics_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","description":"Window, in days back from today.","default":30,"title":"Days"},"description":"Window, in days back from today."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialAnalytics_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/social/accounts":{"get":{"tags":["Social Publishing"],"summary":"List Social Accounts","description":"Connected accounts, their capabilities and this period's publishing capacity.","operationId":"list_social_accounts_social_accounts_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialAccountList_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/social/providers":{"get":{"tags":["Social Publishing"],"summary":"List Social Providers","description":"The ways an account can be connected, and what each can do.","operationId":"list_social_providers_social_providers_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialProviderList_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/social/accounts/{account_id}":{"delete":{"tags":["Social Publishing"],"summary":"Disconnect Social Account","description":"Disconnect an account connected through the official sign-in. 404 for any other kind.\n\nPosts scheduled on it can no longer publish. Reconnecting is a browser sign-in.","operationId":"disconnect_social_account_social_accounts__account_id__delete","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"An `id` from `GET /social/accounts`.","title":"Account Id"},"description":"An `id` from `GET /social/accounts`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialDeleted_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/audience-pipeline/status":{"get":{"tags":["Campaigns"],"summary":"Get Audience Pipeline Status","description":"SPENDS NOTHING. Where the campaign's audience pipeline is, and what it has\nproduced: the list it built, how many contacts, the enrichment job, the\nkeywords it provisioned, and the error if it failed.","operationId":"get_audience_pipeline_status_campaigns__campaign_id__audience_pipeline_status_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id or slug; resolved inside the key's organisation.","title":"Campaign Id"},"description":"Campaign id or slug; resolved inside the key's organisation."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AudiencePipelineStatus_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/audience-pipeline/suggested-filters":{"get":{"tags":["Campaigns"],"summary":"Get Audience Pipeline Suggested Filters","description":"SPENDS NOTHING. The targeting filters the pipeline would build the list from.\n\n`source` says whether they are filters someone accepted or edited\n(`user_modified`) or a fresh extraction from the targeting document\n(`targeting_doc`). 422 when the campaign has no targeting document or it\nyields no filters; generate campaign content first.","operationId":"get_audience_pipeline_suggested_filters_campaigns__campaign_id__audience_pipeline_suggested_filters_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id or slug; resolved inside the key's organisation.","title":"Campaign Id"},"description":"Campaign id or slug; resolved inside the key's organisation."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AudiencePipelineSuggestedFilters_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/audience-pipeline/accept-filters":{"post":{"tags":["Campaigns"],"summary":"Accept Audience Pipeline Filters","description":"SPENDS CREDITS when `run_pipeline` is true, which is the DEFAULT.\n\nSaves the (possibly edited) filters as the campaign's own, then starts the\npipeline: it builds the list, provisions intent keywords and starts a bulk\nenrichment that spends credits per contact. Send `run_pipeline: false` to\nonly save the filters; the answer is then `filters_saved` with no\n`chain_id`. `list_name` overrides the default \"{campaign name} Audience\".","operationId":"accept_audience_pipeline_filters_campaigns__campaign_id__audience_pipeline_accept_filters_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id or slug; resolved inside the key's organisation.","title":"Campaign Id"},"description":"Campaign id or slug; resolved inside the key's organisation."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AudiencePipelineAcceptFiltersRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AudiencePipelineAcceptResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/audience-pipeline/trigger":{"post":{"tags":["Campaigns"],"summary":"Trigger Audience Pipeline","description":"SPENDS CREDITS. Starts the pipeline from the targeting document as it is now.\n\nClears any filters previously accepted for this campaign so they are\nre-extracted from the (possibly edited) document, then dispatches the run:\nlist, intent keywords, bulk enrichment - which spends credits per contact\nwith no ceiling but the list size. 422 when the campaign has no targeting\ndocument with structured data. Poll `status` for progress.","operationId":"trigger_audience_pipeline_campaigns__campaign_id__audience_pipeline_trigger_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id or slug; resolved inside the key's organisation.","title":"Campaign Id"},"description":"Campaign id or slug; resolved inside the key's organisation."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AudiencePipelineTriggerResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/global-context/documents/analytics":{"get":{"tags":["GTM Context"],"summary":"Get Documents Analytics","description":"Every document with its usage counts.\n\nDeclared before `/documents/{doc_id}`: the parameter route would otherwise\nmatch first and try to load a document called \"analytics\".\n\nThe answer to \"which Studio documents are actually being read\" - the input\nto deciding what to regenerate and what to delete.","operationId":"get_documents_analytics_global_context_documents_analytics_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/global-context/documents/buying-journey/crm-status":{"get":{"tags":["GTM Context"],"summary":"Get Buying Journey Crm Status","description":"Whether there is enough CRM data to ground the buying journey.\n\nThe buying journey document is only as good as the closed-won deals behind\nit. This says whether a CRM is connected and how many deals it can see, so\na caller can find out BEFORE generating a document built on nothing.","operationId":"get_buying_journey_crm_status_global_context_documents_buying_journey_crm_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/global-context/documents/{doc_id}":{"get":{"tags":["GTM Context"],"summary":"Get Global Context Document","description":"One document, with its full content.\n\n`GET /global-context/documents` lists them; this returns a single one by id\nor by type key.","operationId":"get_global_context_document_global_context_documents__doc_id__get","parameters":[{"name":"doc_id","in":"path","required":true,"schema":{"type":"string","description":"Document id, OR a document TYPE key. The app resolves either, which is what makes `company_profile` a usable id.","title":"Doc Id"},"description":"Document id, OR a document TYPE key. The app resolves either, which is what makes `company_profile` a usable id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["GTM Context"],"summary":"Update Global Context Document","description":"Update a Global Context (Studio) document's content and/or status.\n\nRead-side counterpart already exists (``GET /global-context/documents``);\nthis closes the long-standing \"read but can't update\" gap for the Context\nbucket. Each save creates a ``DocumentVersion`` snapshot, identical to the\ninternal Studio editor — so version history stays consistent regardless of\nwhether the edit came from the UI, the developer API, or MCP.\n\nPartial update: send ``content``, ``status``, or both. Returns 400 if\nneither is provided, 404 if the document does not exist in this org.\n\nNote: the Intelligence bucket (``cb_intelligence_data``) is intentionally\nread-only — it is machine-generated and has no manual-edit path.","operationId":"update_global_context_document_global_context_documents__doc_id__patch","parameters":[{"name":"doc_id","in":"path","required":true,"schema":{"type":"string","description":"Global context document ID (UUID)","title":"Doc Id"},"description":"Global context document ID (UUID)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateGlobalContextRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/global-context/doc/{doc_type}/highlights":{"get":{"tags":["GTM Context"],"summary":"Get Doc Highlights","description":"The short, quotable points from a completed document.\n\nBuilt for grounding a chat turn without sending the whole document, so this\nis the cheap read when you need a few facts rather than the text.","operationId":"get_doc_highlights_global_context_doc__doc_type__highlights_get","parameters":[{"name":"doc_type","in":"path","required":true,"schema":{"type":"string","description":"Document type key, e.g. `company_profile`, `icp_research`, `buying_journey`. Free-form on purpose: the set grows with the product and a closed list here would 422 a document the org already has.","title":"Doc Type"},"description":"Document type key, e.g. `company_profile`, `icp_research`, `buying_journey`. Free-form on purpose: the set grows with the product and a closed list here would 422 a document the org already has."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/global-context/generate-all":{"post":{"tags":["GTM Context"],"summary":"Generate All Documents","description":"Generate the whole Global Context set, in dependency order.\n\nONE-SHOT. The app refuses this with a 409 once a pipeline has completed for\nthe organisation - it is the onboarding path, not a rebuild. To rebuild\ndocuments that already exist use `POST /global-context/regenerate`.\n\nRequires intelligence data for `website_url` to exist already; without it\nthe documents would be generated from nothing.","operationId":"generate_all_documents_global_context_generate_all_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/GenerateAllDocumentsRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/global-context/scaffold":{"post":{"tags":["GTM Context"],"summary":"Scaffold All Documents","description":"Create every Global Context document as an EMPTY template.\n\nScaffolding is not generation: it creates the rows so the library has a\nshape, and leaves them empty. Useful when you want to fill documents\nyourself through `PATCH /global-context/documents/{doc_id}` rather than\nhave them written for you.","operationId":"scaffold_all_documents_global_context_scaffold_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/global-context/scaffold-company-profile":{"post":{"tags":["GTM Context"],"summary":"Scaffold Company Profile","description":"Create the `company_profile` template if it does not exist.\n\nIDEMPOTENT - an org that already has one gets the existing document back\nrather than a second copy. The company profile is the root of the\ndependency graph, so this is the one to create first when a library is\nmissing it.","operationId":"scaffold_company_profile_global_context_scaffold_company_profile_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/global-context/scaffold-company-keywords":{"post":{"tags":["GTM Context"],"summary":"Scaffold Company Keywords","description":"Create the Company Keywords template in the brand category. IDEMPOTENT.","operationId":"scaffold_company_keywords_global_context_scaffold_company_keywords_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/global-context/extract-company-data":{"post":{"tags":["GTM Context"],"summary":"Extract Company Data","description":"Pull company facts out of scraped intelligence data.\n\nSPENDS CREDITS when `enrich` is true (the default): the route is\ncredit-gated before the model call and answers 402 when the balance is\nshort. Send `enrich=false` for the scrape-derived fields alone, which costs\nnothing extra.\n\nThe app takes an untyped body here; this contract types it, so a missing\n`website_url` is a 422 naming the field rather than a 400 describing it.","operationId":"extract_company_data_global_context_extract_company_data_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ExtractCompanyDataRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/global-context/pipelines":{"get":{"tags":["GTM Context"],"summary":"List Pipelines","description":"Recent Global Context generation runs, newest first.","operationId":"list_pipelines_global_context_pipelines_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"How many recent runs to return. The app's default is 10.","default":10,"title":"Limit"},"description":"How many recent runs to return. The app's default is 10."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/global-context/pipeline/latest":{"get":{"tags":["GTM Context"],"summary":"Get Latest Pipeline","description":"The most recent run.\n\nDeclared before `/pipeline/{pipeline_id}` so the literal wins - otherwise\nthe id route matches \"latest\" and looks for a pipeline with that id.","operationId":"get_latest_pipeline_global_context_pipeline_latest_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/global-context/pipeline/{pipeline_id}":{"get":{"tags":["GTM Context"],"summary":"Get Pipeline Status","description":"Per-document status for ONE run.\n\nThis is where a stalled generation is diagnosed: which documents completed,\nwhich are still generating, and which failed with what.","operationId":"get_pipeline_status_global_context_pipeline__pipeline_id__get","parameters":[{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","description":"Pipeline id.","title":"Pipeline Id"},"description":"Pipeline id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/global-context/resume-pipeline":{"post":{"tags":["GTM Context"],"summary":"Resume Pipeline","description":"Finish a run that stopped part way, generating only what is missing.\n\nThe repair for a pipeline that died mid-way. It does NOT rebuild documents\nthat already completed, so it is cheap and safe to retry.","operationId":"resume_pipeline_global_context_resume_pipeline_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/global-context/reset-stuck-documents":{"post":{"tags":["GTM Context"],"summary":"Reset Stuck Documents","description":"Move documents wedged in `generating` back to a state you can act on.\n\nA document whose worker died stays `generating` forever and blocks a\nretry. This unblocks them; it does not generate anything.","operationId":"reset_stuck_documents_global_context_reset_stuck_documents_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/global-context/stop-all-generation":{"post":{"tags":["GTM Context"],"summary":"Stop All Generation","description":"Stop every in-flight generation for this organisation, immediately.\n\nThe kill switch. Work already done is kept; work in flight is abandoned,\nso a document caught mid-write comes back as failed rather than partial.","operationId":"stop_all_generation_global_context_stop_all_generation_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/global-context/reindex-all":{"post":{"tags":["GTM Context"],"summary":"Reindex All Documents","description":"Re-index every document into retrieval.\n\nChanges no document. It rebuilds the index the copilot and campaign\ngeneration search, which is the fix when a document reads correctly in the\nlibrary but never shows up as grounding.","operationId":"reindex_all_documents_global_context_reindex_all_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/global-context/documents/{doc_id}/feedback":{"post":{"tags":["GTM Context"],"summary":"Submit Document Feedback","description":"Thumbs up or down on a document.\n\n`usage_id` attaches the feedback to a specific USE of the document rather\nthan to the document itself, which is what makes \"this answer was wrong\"\ndistinguishable from \"this document is wrong\".","operationId":"submit_document_feedback_global_context_documents__doc_id__feedback_post","parameters":[{"name":"doc_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Doc Id"},"description":"Document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DocumentFeedbackRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/global-context/documents/buying-journey/interview":{"post":{"tags":["GTM Context"],"summary":"Save Buying Journey Interview","description":"Record how this organisation actually sells, in its own words.\n\nThe answers are injected as HIGHEST-PRIORITY grounding the next time the\nbuying journey is generated - they outrank the scraped and inferred\nmaterial. The document must already exist; this grounds it, it does not\ncreate it.\n\nDeclared with a literal `buying-journey` second segment, so it does not\ncollide with `/documents/{doc_id}/feedback`.","operationId":"save_buying_journey_interview_global_context_documents_buying_journey_interview_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BuyingJourneyInterviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/global-context/documents":{"delete":{"tags":["GTM Context"],"summary":"Delete All Documents","description":"Delete EVERY Global Context document for this organisation.\n\nNOT REVERSIBLE, and it is the whole library: every ICP, persona, buying\njourney and profile the org has. Everything downstream that grounds on them\n- campaign generation, the copilot, retrieval - is generating from nothing\nuntil they are rebuilt.\n\nThe narrower operation is `DELETE /global-context/documents/{doc_type}`.","operationId":"delete_all_documents_global_context_documents_delete","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"},"get":{"tags":["GTM Context"],"summary":"List Global Context Documents","description":"List global context documents for the authenticated organization.\n\nEach row carries metadata (id, display_name, file_type, category,\nfolder_path, status, priority, version, timestamps), plus `wiki_category`\n(the group the Studio Wiki shows it under) and `workflow` (context,\nintelligence or research). When ``include_content`` is True (the default)\nthe document body is included at ``content`` (sourced from\n``meta_data.content``) so callers can read what a document actually says;\npass ``include_content=false`` to omit the body for a cheaper listing. The\ndefault stays True for backwards compatibility — the MCP\n``g8_gtm_get_global_context`` tool, the JS SDK ``studio.globalContext``\nclient, and the ``g8://global-context`` resource surfaces have always relied\non ``content`` being present.\n\n``include_intelligence`` / ``include_research`` add the Wiki's other two\nbuckets so a caller can see every Wiki document in one call; ``limit``\napplies to each bucket.","operationId":"list_global_context_documents_global_context_documents_get","parameters":[{"name":"category","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by context category: brand, audience, messaging, market, offer, targeting, data (case-insensitive). `targeting` matches the Studio Wiki's Targeting group (TAM / ICP / Persona Research). An unknown category that matches no document returns 422 listing the valid categories.","title":"Category"},"description":"Filter by context category: brand, audience, messaging, market, offer, targeting, data (case-insensitive). `targeting` matches the Studio Wiki's Targeting group (TAM / ICP / Persona Research). An unknown category that matches no document returns 422 listing the valid categories."},{"name":"include_content","in":"query","required":false,"schema":{"type":"boolean","description":"Include each document's body text at `content` (read from meta_data.content). Default True preserves historical behavior (this endpoint has always returned content); pass false for a lighter metadata-only listing.","default":true,"title":"Include Content"},"description":"Include each document's body text at `content` (read from meta_data.content). Default True preserves historical behavior (this endpoint has always returned content); pass false for a lighter metadata-only listing."},{"name":"include_intelligence","in":"query","required":false,"schema":{"type":"boolean","description":"Also list the Wiki's Intelligence documents (website scrape, competitor discovery, organic keywords, brand news, ...) with `workflow`='intelligence' and category 'data'. Metadata only: read a body with GET /intelligence-data ?data_type=<file_type>&include_content=true. Default false (historical shape).","default":false,"title":"Include Intelligence"},"description":"Also list the Wiki's Intelligence documents (website scrape, competitor discovery, organic keywords, brand news, ...) with `workflow`='intelligence' and category 'data'. Metadata only: read a body with GET /intelligence-data ?data_type=<file_type>&include_content=true. Default false (historical shape)."},{"name":"include_research","in":"query","required":false,"schema":{"type":"boolean","description":"Also list the Wiki's Research reports with `workflow`='research' and category 'data'; `content` carries the report markdown when include_content is true. Default false (historical shape).","default":false,"title":"Include Research"},"description":"Also list the Wiki's Research reports with `workflow`='research' and category 'data'; `content` carries the report markdown when include_content is true. Default false (historical shape)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/global-context/documents/{doc_type}":{"delete":{"tags":["GTM Context"],"summary":"Delete Document","description":"Delete ONE document, by TYPE rather than by id.\n\nThe path parameter is a type key, not a document id - deleting\n`company_profile` removes whichever document currently holds that type.\nNot reversible.","operationId":"delete_document_global_context_documents__doc_type__delete","parameters":[{"name":"doc_type","in":"path","required":true,"schema":{"type":"string","description":"Document type key, e.g. `company_profile`, `icp_research`, `buying_journey`. Free-form on purpose: the set grows with the product and a closed list here would 422 a document the org already has.","title":"Doc Type"},"description":"Document type key, e.g. `company_profile`, `icp_research`, `buying_journey`. Free-form on purpose: the set grows with the product and a closed list here would 422 a document the org already has."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/global-context/{doc_id}/regenerate":{"post":{"tags":["GTM Context"],"summary":"Regenerate One Document","description":"Rewrite ONE document with AI, from the current intelligence data.\n\nDifferent from `POST /global-context/regenerate`, which rebuilds a SET\nagainst a website: this takes a single document id and rewrites it in\nplace. The old content is replaced.\n\nDeclared LAST on this router. `{doc_id}` occupies the same segment as every\nliteral above it, so registered earlier it would swallow `/pipelines`,\n`/scaffold` and the rest.","operationId":"regenerate_one_document_global_context__doc_id__regenerate_post","parameters":[{"name":"doc_id","in":"path","required":true,"schema":{"type":"string","description":"Document id.","title":"Doc Id"},"description":"Document id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/global-context/documents/{doc_id}/track-usage":{"post":{"tags":["GTM Context"],"summary":"Track Document Usage","description":"Record one use of a Global Context document.\n\nFeeds `GET /global-context/documents/analytics`. 404 if the document does\nnot exist in the caller's organisation.","operationId":"track_document_usage_global_context_documents__doc_id__track_usage_post","parameters":[{"name":"doc_id","in":"path","required":true,"schema":{"type":"string","description":"Global Context document ID.","title":"Doc Id"},"description":"Global Context document ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TrackDocumentUsageRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/enablement/assets":{"post":{"tags":["GTM Context"],"summary":"Upload Enablement Asset","description":"Upload an internal, org-scoped asset to Studio's Enablement library.","operationId":"upload_enablement_asset_enablement_assets_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EnablementAssetUploadRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/company-profile":{"get":{"tags":["GTM Context"],"summary":"Get Company Profile","description":"Read this org's company profile — the source Studio generation reads from.\n\nReturns the most recently updated profile (``_ordered_profile_candidates``\norders by ``updated_at`` desc, then ``created_at`` desc, then ``id`` desc, and\nthis takes the first row). It does NOT filter by a confirmed domain, so after a\ndomain change the row you get back is whichever profile was touched last — call\n``PUT /company-profile`` to set the correct one if the latest is stale.","operationId":"get_company_profile_company_profile_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"put":{"tags":["GTM Context"],"summary":"Update Company Profile","description":"Set this org's company profile (website + fields).\n\n**Why this exists.** The company profile is the source of truth for Studio\ngeneration. Self-serve orgs that sign up without a domain get a profile seeded\nwith graph8's own details, so every generated document describes the wrong\ncompany — and the only write path was ``POST /company-profile``, an internal\nJWT route absent from both the developer API and MCP. An agent could therefore\ndetect the problem but never fix it, and could not even read the field back to\nconfirm a human had fixed it.\n\nApproved profiles are immutable. Pass ``unapprove_if_approved: true`` to\ndeliberately unlock and overwrite one; otherwise this returns 409 rather than\nquietly discarding a human's approval.\n\nChanging the website does NOT regenerate existing Studio documents — they were\ngenerated from the old site. Follow with\n``POST /api/v1/global-context/regenerate``.","operationId":"update_company_profile_company_profile_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CompanyProfileUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/global-context/regenerate":{"post":{"tags":["GTM Context"],"summary":"Regenerate Global Context","description":"Regenerate Studio (Global Context) documents against a website.\n\n**Why this exists.** Studio docs are generated once at onboarding from the\ncompany profile's website. If that profile was wrong at the time — the common\ncase for self-serve orgs, which seed graph8's own profile when no domain is\ngiven — every downstream ICP, persona, TAM and campaign is built on the wrong\ncompany, and there was no machine path to fix it:\n\n* the internal ``POST /global-context/generate-all`` refuses forever once the\n  first pipeline completes (``409 ... Contact support to reset and regenerate``);\n* ``POST /global-context/generate/{doc_type}`` has no such lock but was\n  JWT-only, so an agent or API key could not call it.\n\nThis endpoint wraps the per-document path, which means it is **not** subject to\nthe one-shot pipeline lock and can be run whenever the source of truth changes.\n\nRequires intelligence data for ``website_url`` to exist already — run the\nintelligence analyze step first for a newly-changed domain, otherwise this\nreturns 404 rather than regenerating stale content.","operationId":"regenerate_global_context_global_context_regenerate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RegenerateContextRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/personas":{"get":{"tags":["GTM Context"],"summary":"List Personas","description":"List campaign-builder personas for the authenticated organization.","operationId":"list_personas_personas_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by persona status","title":"Status"},"description":"Filter by persona status"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"post":{"tags":["GTM Context"],"summary":"Create Persona","description":"Create a Studio buyer persona (manual - no AI generation).\n\nRead-side counterpart already exists (``GET /personas``); this closes the\n\"read but can't create\" gap for the Persona bucket. The new persona is created\nwith status 'active' and returned in the same shape as ``GET /personas``.","operationId":"create_persona_personas_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreatePersonaRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/personas/{persona_id}":{"patch":{"tags":["GTM Context"],"summary":"Update Persona","description":"Update a Studio persona's fields and/or status (partial update).\n\nSend at least one field. Passing ``status='archived'`` is equivalent to\n``POST /personas/{persona_id}/archive``. Returns 400 if no field is provided,\n404 if the persona does not exist in this org.","operationId":"update_persona_personas__persona_id__patch","parameters":[{"name":"persona_id","in":"path","required":true,"schema":{"type":"string","description":"Persona ID (UUID)","title":"Persona Id"},"description":"Persona ID (UUID)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdatePersonaRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"get":{"tags":["GTM Library"],"summary":"Get Persona","description":"One persona.","operationId":"get_persona_personas__persona_id__get","parameters":[{"name":"persona_id","in":"path","required":true,"schema":{"type":"string","description":"Persona id.","title":"Persona Id"},"description":"Persona id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"delete":{"tags":["GTM Library"],"summary":"Delete Persona","description":"Permanently delete a persona. `POST /personas/{id}/archive` is the reversible option.","operationId":"delete_persona_personas__persona_id__delete","parameters":[{"name":"persona_id","in":"path","required":true,"schema":{"type":"string","description":"Persona id.","title":"Persona Id"},"description":"Persona id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/personas/{persona_id}/archive":{"post":{"tags":["GTM Context"],"summary":"Archive Persona","description":"Archive a Studio persona (soft delete - sets status='archived').\n\nArchived personas drop out of the default ``GET /personas`` listing but remain\nfetchable via ``?status=archived``. Returns 404 if the persona does not exist.","operationId":"archive_persona_personas__persona_id__archive_post","parameters":[{"name":"persona_id","in":"path","required":true,"schema":{"type":"string","description":"Persona ID (UUID)","title":"Persona Id"},"description":"Persona ID (UUID)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/icps":{"get":{"tags":["GTM Context"],"summary":"List Icps","description":"List campaign-builder ICPs for the authenticated organization.","operationId":"list_icps_icps_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by ICP status","title":"Status"},"description":"Filter by ICP status"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"post":{"tags":["GTM Context"],"summary":"Create Icp","description":"Create a Studio ICP (manual - no AI generation).\n\nRead-side counterpart already exists (``GET /icps``); this closes the\n\"read but can't create\" gap for the ICP bucket. The new ICP is created with\nstatus 'active' and returned in the same shape as ``GET /icps``.","operationId":"create_icp_icps_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateIcpRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/icps/{icp_id}":{"patch":{"tags":["GTM Context"],"summary":"Update Icp","description":"Update a Studio ICP's fields (partial update).\n\nSend at least one field. To archive an ICP use ``POST /icps/{icp_id}/archive``.\nReturns 400 if no field is provided, 404 if the ICP does not exist in this org.","operationId":"update_icp_icps__icp_id__patch","parameters":[{"name":"icp_id","in":"path","required":true,"schema":{"type":"string","description":"ICP ID (UUID)","title":"Icp Id"},"description":"ICP ID (UUID)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateIcpRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/icps/{icp_id}/archive":{"post":{"tags":["GTM Context"],"summary":"Archive Icp","description":"Archive a Studio ICP (soft delete - sets status='archived').\n\nArchived ICPs drop out of the default ``GET /icps`` listing but remain fetchable\nvia ``?status=archived``. Returns 404 if the ICP does not exist.","operationId":"archive_icp_icps__icp_id__archive_post","parameters":[{"name":"icp_id","in":"path","required":true,"schema":{"type":"string","description":"ICP ID (UUID)","title":"Icp Id"},"description":"ICP ID (UUID)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/mailboxes/{mailbox_id}/warmup":{"get":{"tags":["GTM Context"],"summary":"Get Mailbox Warmup Analytics","description":"Get live warmup analytics for a single mailbox.\n\nWraps the existing ``GET /warmup/{mailbox_id}/analytics`` flow so MCP\n(API-key auth) can read warmup engagement / reputation without going\nthrough cookie-based session auth.\n\nBehavior:\n    - Looks up the mailbox in the API user's org schema. 404 if missing\n      or deleted. Tenant isolation comes from the per-org schema bind,\n      NOT from a row-level predicate.\n    - Hits the configured warmup provider (Instantly or SmartLead) over\n      HTTP — slow (~300-800ms typical). For warm bulk reads use\n      ``list_mailboxes`` and check the cheap DB-level ``warmup_status``.\n    - Returns ``{success, warmup_enabled, provider, analytics, warmup_settings}``\n      — same shape as the internal /warmup/{id}/analytics endpoint.\n\nBackwards-compat: this is a brand-new route. The internal\n/warmup/{id}/analytics (cookie auth) is unchanged.\n\nHistorical bug (fixed 2026-05-24, same root cause as list_mailboxes\nabove): the previous implementation appended\n``(t.org_id = :org_id OR m.created_by = :user_id)`` to the WHERE. Both\nhalves match zero rows in prod — ``mailboxes.team_id`` is NULL on every\nrow (no team pinning) and ``mailboxes.created_by`` stores email strings,\nnot propelauth UUIDs. Result: every warmup-analytics call 404'd even\nfor mailboxes that ``list_mailboxes`` happily returned. Dropping the\npredicate restores parity; schema bind is the tenant boundary.","operationId":"get_mailbox_warmup_analytics_mailboxes__mailbox_id__warmup_get","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","title":"Mailbox Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/intelligence-data":{"get":{"tags":["GTM Context"],"summary":"List Intelligence Data","description":"List intelligence-data documents (the ~16 docs in the Intelligence bucket).\n\nPart of the 44-document Studio Global Document Architecture (21 context +\n16 intelligence + 6 research + 1 brief). The MCP campaign-ideation path\nneeds this bucket — historically only the ``cb_global_contexts`` (Context)\nbucket was exposed via REST.","operationId":"list_intelligence_data_intelligence_data_get","parameters":[{"name":"data_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by data_type (website_scrape, company_enrichment, competitor_discovery, company_keywords, product_inventory, organic_keywords, paid_keywords, ...)","title":"Data Type"},"description":"Filter by data_type (website_scrape, company_enrichment, competitor_discovery, company_keywords, product_inventory, organic_keywords, paid_keywords, ...)"},{"name":"include_content","in":"query","required":false,"schema":{"type":"boolean","description":"Include the raw `data` JSONB blob (large; default omits)","default":false,"title":"Include Content"},"description":"Include the raw `data` JSONB blob (large; default omits)"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/research-reports":{"get":{"tags":["GTM Context"],"summary":"List Research Reports","description":"List research-report documents (the 6 docs in the Research bucket).\n\nPart of the 44-document Studio Global Document Architecture (21 context +\n16 intelligence + 6 research + 1 brief). The MCP ideation path needs this\nbucket alongside ``/intelligence-data`` to surface the full picture.","operationId":"list_research_reports_research_reports_get","parameters":[{"name":"report_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by report_type (buyer_psychology, competitive_teardown, gtm_channel, industry_analyst, review_sentiment, voice_of_customer)","title":"Report Type"},"description":"Filter by report_type (buyer_psychology, competitive_teardown, gtm_channel, industry_analyst, review_sentiment, voice_of_customer)"},{"name":"include_content","in":"query","required":false,"schema":{"type":"boolean","description":"Include the structured `content` JSONB blob + markdown (large)","default":false,"title":"Include Content"},"description":"Include the structured `content` JSONB blob + markdown (large)"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/activities":{"get":{"tags":["GTM Context"],"summary":"List Activities","description":"List recent activities for the authenticated organization.","operationId":"list_activities_activities_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"activity_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Activity Type"}},{"name":"contact_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contact Id"}},{"name":"company_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Id"}},{"name":"mashup_contact_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Mashup Contact Id"}},{"name":"mashup_company_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Mashup Company Id"}},{"name":"deal_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Deal Id"}},{"name":"occurred_after","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Occurred After"}},{"name":"occurred_before","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Occurred Before"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/brand-kit":{"get":{"tags":["Brand Kit"],"summary":"Get Brand Kit Overview","description":"Everything the Brand Kit knows about this organisation, in one read.\n\nDesign tokens, the measured colour palette, fonts, whether a homepage has\nbeen captured and whether templates have been built. The orientation call:\nread this first to find out which of the other routes there is any point\ncalling.","operationId":"get_brand_kit_overview_brand_kit_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/brand-kit/homepage":{"get":{"tags":["Brand Kit"],"summary":"Get Brand Kit Homepage","description":"The cloned homepage HTML captured during brand extraction.\n\nThis is the raw source everything else here is derived from. It can be\nlarge - a real homepage with inlined CSS - so prefer `/brand-kit/sections`\nwhen you want the structure rather than the bytes.","operationId":"get_brand_kit_homepage_brand_kit_homepage_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/brand-kit/homepage/recapture":{"post":{"tags":["Brand Kit"],"summary":"Recapture Homepage Html","description":"Re-capture the homepage for full CSS fidelity.\n\nREPLACES the stored capture. Reaches an external scraping provider, so it\nis slower and costlier than anything else here - run it when the customer's\nsite has actually changed, not as a refresh.","operationId":"recapture_homepage_html_brand_kit_homepage_recapture_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/brand-kit/sections":{"get":{"tags":["Brand Kit"],"summary":"Get Homepage Sections","description":"The homepage broken into its visual sections.\n\nDerived live from the stored capture, so it changes when the capture does\nand nothing needs rebuilding. The durable, multi-page version is\n`/brand-kit/section-library`.","operationId":"get_homepage_sections_brand_kit_sections_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/brand-kit/extract":{"post":{"tags":["Brand Kit"],"summary":"Trigger Brand Extraction","description":"Start, or restart, brand extraction.\n\nOmit the body to re-extract the website already on the org's company\nprofile. Supplying `website_url` EXTRACTS A DIFFERENT SITE and replaces\nthe org's design tokens and homepage capture with that site's - which is\nhow a brand kit ends up belonging to the wrong company. Asynchronous; the\nresult appears on `GET /brand-kit`.","operationId":"trigger_brand_extraction_brand_kit_extract_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/BrandExtractionRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/brand-kit/re-extract":{"post":{"tags":["Brand Kit"],"summary":"Re Extract Design System","description":"Re-scrape the website and rebuild the Design system. SPENDS CREDITS (it can regenerate the style guide).\n\nRebuilds the brand snapshot, and the style guide when the URL changed. It does not touch the organisation's primary\nwebsite, content sources or company profile. `website_url` is REQUIRED (unlike `POST /brand-kit/extract`). The app's\nown guards apply: 402 when the organisation cannot pay (`check_credits` runs inside the handler, before anything is\nqueued), 400 for a URL that is not a public site, 409 while a re-extract or a document run is already going, 429\nfor a minute after one starts. Asynchronous: poll `GET /brand-kit/re-extract/status`.","operationId":"re_extract_design_system_brand_kit_re_extract_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BrandReExtractRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/brand-kit/re-extract/status":{"get":{"tags":["Brand Kit"],"summary":"Get Re Extract Status","description":"Where the last re-extract is: `generating` with its `phase`, or `idle` when nothing ran within the status window.","operationId":"get_re_extract_status_brand_kit_re_extract_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/brand-kit/section-library":{"get":{"tags":["Brand Kit"],"summary":"Get Section Library","description":"Every section in the org's library, across all crawled pages.","operationId":"get_section_library_brand_kit_section_library_get","parameters":[{"name":"include_code","in":"query","required":false,"schema":{"type":"boolean","description":"Include each section's full HTML and CSS. Off by default because the response is an order of magnitude larger with it on - use the detail route for a single preview, and this only for a bulk export.","default":false,"title":"Include Code"},"description":"Include each section's full HTML and CSS. Off by default because the response is an order of magnitude larger with it on - use the detail route for a single preview, and this only for a bulk export."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/brand-kit/section-library/candidate-pages":{"get":{"tags":["Brand Kit"],"summary":"List Candidate Pages For Section Library","description":"The pages a rebuild could draw sections from.\n\nDeclared BEFORE `/section-library/{section_id}`. The app declares them the\nother way round, so in the app this path is matched by the detail route and\nresolves a section id of \"candidate-pages\" instead. Read this to choose\n`page_urls` for a rebuild.","operationId":"list_candidate_pages_for_section_library_brand_kit_section_library_candidate_pages_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/brand-kit/section-library/rebuild":{"post":{"tags":["Brand Kit"],"summary":"Rebuild Section Library","description":"Rebuild the section library. REPLACES what is there.\n\nThe two overrides are not interchangeable: `page_urls` REPLACES the\nautomatic page selection, `extra_page_urls` ADDS to it. Send neither to let\nthe picker choose. Asynchronous.","operationId":"rebuild_section_library_brand_kit_section_library_rebuild_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/SectionLibraryRebuildRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/brand-kit/section-library/{section_id}":{"get":{"tags":["Brand Kit"],"summary":"Get Section Library Item","description":"One section, with self-contained HTML ready to render in an iframe.\n\nSelf-contained means the CSS travels with it - this is the preview call,\nand the reason `include_code` is off on the list route.","operationId":"get_section_library_item_brand_kit_section_library__section_id__get","parameters":[{"name":"section_id","in":"path","required":true,"schema":{"type":"string","description":"Section id.","title":"Section Id"},"description":"Section id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/brand-kit/section-tag-overrides":{"get":{"tags":["Brand Kit"],"summary":"Get Section Tag Overrides","description":"Durable per-section tag and category overrides.\n\nTags are derived automatically; these are the corrections that survive a\nrebuild. Without them, every rebuild re-derives the same wrong tag.","operationId":"get_section_tag_overrides_brand_kit_section_tag_overrides_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"put":{"tags":["Brand Kit"],"summary":"Save Section Tag Overrides","description":"Upsert tag overrides, keyed by section id.\n\nUPSERT, not replace: sections you do not mention keep the overrides they\nalready had. To clear one, send it with empty lists.","operationId":"save_section_tag_overrides_brand_kit_section_tag_overrides_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SectionTagOverridesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/brand-kit/templates":{"get":{"tags":["Brand Kit"],"summary":"Get Brand Kit Templates","description":"The org-level landing page templates a campaign can be built on.","operationId":"get_brand_kit_templates_brand_kit_templates_get","parameters":[{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^(layout_archetype|homepage)$"},{"type":"null"}],"description":"`layout_archetype` for templates built from a chosen archetype, `homepage` for the one cloned from the org's own site. Omit for both.","title":"Source"},"description":"`layout_archetype` for templates built from a chosen archetype, `homepage` for the one cloned from the org's own site. Omit for both."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Brand Kit"],"summary":"Delete Brand Kit Templates","description":"Delete org-level templates so they can be regenerated.\n\nOMITTING `source` DELETES BOTH KINDS. Not reversible, and a campaign built\non a deleted template keeps its own copy - this removes the org-level\noriginal, not the pages already made from it.","operationId":"delete_brand_kit_templates_brand_kit_templates_delete","parameters":[{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^(layout_archetype|homepage)$"},{"type":"null"}],"description":"`layout_archetype` for templates built from a chosen archetype, `homepage` for the one cloned from the org's own site. Omit for both.","title":"Source"},"description":"`layout_archetype` for templates built from a chosen archetype, `homepage` for the one cloned from the org's own site. Omit for both."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/brand-kit/templates/status":{"get":{"tags":["Brand Kit"],"summary":"Get Template Generation Status","description":"Whether template generation is running, finished or failed.","operationId":"get_template_generation_status_brand_kit_templates_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/brand-kit/archetypes":{"get":{"tags":["Brand Kit"],"summary":"List Archetypes","description":"The catalogue of landing page layout archetypes.\n\nGLOBAL, not per-organisation: the same catalogue for everyone. Your org's\npicks from it are `/brand-kit/layout-selections`.","operationId":"list_archetypes_brand_kit_archetypes_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/brand-kit/layout-selections":{"get":{"tags":["Brand Kit"],"summary":"Get Layout Selections","description":"Which layout archetypes this organisation has chosen.","operationId":"get_layout_selections_brand_kit_layout_selections_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"put":{"tags":["Brand Kit"],"summary":"Save Layout Selections","description":"REPLACE the org's layout archetype selection.\n\nSelecting is not building: the templates are produced by\n`POST /brand-kit/layout-templates/regenerate` afterwards.","operationId":"save_layout_selections_brand_kit_layout_selections_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LayoutSelectionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/brand-kit/layout-templates/regenerate":{"post":{"tags":["Brand Kit"],"summary":"Regenerate Layout Templates","description":"Build the landing page templates for the selected archetypes.\n\nAsynchronous. Poll `GET /brand-kit/layout-templates/status` for per-archetype\nprogress.","operationId":"regenerate_layout_templates_brand_kit_layout_templates_regenerate_post","parameters":[{"name":"archetype_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Rebuild ONE archetype's template. Omit to run the layout picker and rebuild every selected archetype - which is much more work.","title":"Archetype Id"},"description":"Rebuild ONE archetype's template. Omit to run the layout picker and rebuild every selected archetype - which is much more work."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/brand-kit/layout-templates/status":{"get":{"tags":["Brand Kit"],"summary":"Get Layout Templates Status","description":"Per-archetype template build progress.","operationId":"get_layout_templates_status_brand_kit_layout_templates_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/brand-kit/layout-templates/custom":{"get":{"tags":["Brand Kit"],"summary":"List Custom Layout Templates","description":"The idea-driven templates already built for this organisation.","operationId":"list_custom_layout_templates_brand_kit_layout_templates_custom_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"post":{"tags":["Brand Kit"],"summary":"Create Custom Layout Template","description":"Queue one landing page template built from a plain-language idea.\n\nPass the `plan` returned by `/layout-templates/custom/plan` to build the\npage you previewed; omit it and the idea is re-interpreted from scratch,\nwhich will not match the preview.\n\n`attached_assets` are MANDATORY inclusions, not suggestions - the generated\npage uses them. Capped at 5 images and 2 videos.","operationId":"create_custom_layout_template_brand_kit_layout_templates_custom_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CustomLayoutTemplateRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/brand-kit/layout-templates/custom/plan":{"post":{"tags":["Brand Kit"],"summary":"Plan Custom Template","description":"Preview the section plan for an idea. Builds nothing, stores nothing.\n\nThe review step: it returns the plan a build WOULD follow, so the plan can\nbe edited and handed back to `POST /layout-templates/custom` instead of\ndiscovering the interpretation was wrong after the page exists.","operationId":"plan_custom_template_brand_kit_layout_templates_custom_plan_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CustomTemplatePlanRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/brand-kit/layout-templates/improve-idea":{"post":{"tags":["Brand Kit"],"summary":"Improve Custom Template Idea","description":"Rewrite a one-line idea into a fuller brief. Changes nothing.","operationId":"improve_custom_template_idea_brand_kit_layout_templates_improve_idea_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ImproveIdeaRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/brand-kit/layout-templates/custom/{landing_page_id}/regenerate":{"post":{"tags":["Brand Kit"],"summary":"Regenerate Custom Layout Template","description":"Re-run a custom build with the same idea. REPLACES the template.","operationId":"regenerate_custom_layout_template_brand_kit_layout_templates_custom__landing_page_id__regenerate_post","parameters":[{"name":"landing_page_id","in":"path","required":true,"schema":{"type":"string","description":"The custom template to rebuild.","title":"Landing Page Id"},"description":"The custom template to rebuild."},{"name":"clear_plan","in":"query","required":false,"schema":{"type":"boolean","description":"Discard the stored plan and re-derive one from the original idea. Leave false to rebuild against the plan that was approved.","default":false,"title":"Clear Plan"},"description":"Discard the stored plan and re-derive one from the original idea. Leave false to rebuild against the plan that was approved."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/brand-kit/newsletter-archetypes":{"get":{"tags":["Brand Kit"],"summary":"List Newsletter Archetypes","description":"The catalogue of newsletter archetypes. GLOBAL, not per-organisation.","operationId":"list_newsletter_archetypes_brand_kit_newsletter_archetypes_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/brand-kit/newsletter-selections":{"get":{"tags":["Brand Kit"],"summary":"Get Newsletter Selections","description":"Which newsletter archetypes this organisation has chosen.","operationId":"get_newsletter_selections_brand_kit_newsletter_selections_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"put":{"tags":["Brand Kit"],"summary":"Save Newsletter Selections","description":"REPLACE the org's newsletter archetype selection.","operationId":"save_newsletter_selections_brand_kit_newsletter_selections_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NewsletterSelectionsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/brand-kit/newsletter-templates":{"get":{"tags":["Brand Kit"],"summary":"List Newsletter Templates","description":"The newsletter templates built from this org's Brand Kit picks.","operationId":"list_newsletter_templates_brand_kit_newsletter_templates_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/brand-kit/newsletter-templates/regenerate":{"post":{"tags":["Brand Kit"],"summary":"Regenerate Newsletter Templates","description":"Build newsletter templates for the selected archetypes. Asynchronous.","operationId":"regenerate_newsletter_templates_brand_kit_newsletter_templates_regenerate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/brand-kit/newsletter-templates/status":{"get":{"tags":["Brand Kit"],"summary":"Get Newsletter Templates Status","description":"Per-archetype newsletter template build progress.","operationId":"get_newsletter_templates_status_brand_kit_newsletter_templates_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/org/settings":{"get":{"tags":["Organization Settings"],"summary":"Get Org Settings","description":"The organisation's name, auto-join domain and signup URL.\n\n`email_domain` is the auto-join domain: anyone signing up with an address\nat it joins THIS organisation with no invite. Read it before you trust the\norg's membership to be invite-only.","operationId":"get_org_settings_org_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Organization Settings"],"summary":"Update Org Settings","description":"Rename the organisation, or set its auto-join email domain.\n\nSETTING `email_domain` WIDENS WHO CAN JOIN. Anyone who signs up with an\naddress at that domain becomes a member without an invite. Admin-gated, and\nthe handler re-checks the caller's org role on top.\n\nThe rename happens FIRST and against PropelAuth, so a rejected name aborts\nthe whole update rather than half-applying it.","operationId":"update_org_settings_org_settings_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OrgSettingsUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/settings/docs":{"get":{"tags":["Organization Settings"],"summary":"Get Doc Settings","description":"Which documents are generated by default, for every scope at once.\n\nThe source of the `default_doc_ids` a contact, account, prospect, campaign\nor global generation starts from. `mandatory_doc_ids` are the ones a user\ncannot switch off in the UI.","operationId":"get_doc_settings_org_settings_docs_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/org/settings/docs/meetings":{"get":{"tags":["Organization Settings"],"summary":"Get Meeting Extraction Settings","description":"How a meeting transcript is read: grounding, fields, glossary.\n\n`meeting_grounding` is what tells the extractor which attendees are YOURS -\nthe canonical company name, the internal email domains and the brand\naliases. Get it wrong and every meeting is classified as external.","operationId":"get_meeting_extraction_settings_org_settings_docs_meetings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Organization Settings"],"summary":"Update Meeting Extraction Settings","description":"Replace the meeting extraction settings.\n\nDeclared BEFORE `PUT /org/settings/docs/{scope}`: the other way round the\nparameter route matches first, binds `scope` to \"meetings\", and the Literal\nrejects it - a 422 on a route that exists.\n\nEvery block defaults to EMPTY, so omitting one is not the same as leaving\nit alone. Read the current settings, change what you need, send the whole\nobject back.","operationId":"update_meeting_extraction_settings_org_settings_docs_meetings_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MeetingExtractionSettingsUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/settings/docs/{scope}":{"put":{"tags":["Organization Settings"],"summary":"Update Doc Settings","description":"Set the default documents for ONE scope.\n\n`mandatory_doc_ids` omitted leaves the current mandatory set alone; sending\nan empty list CLEARS it. The two are different instructions and only one is\ndestructive.","operationId":"update_doc_settings_org_settings_docs__scope__put","parameters":[{"name":"scope","in":"path","required":true,"schema":{"enum":["contacts","accounts","prospects","campaigns","global"],"type":"string","description":"Which generation scope these defaults apply to.","title":"Scope"},"description":"Which generation scope these defaults apply to."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DocSettingsUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/settings/docs/folders/{scope}":{"get":{"tags":["Organization Settings"],"summary":"Get Doc Folder Template","description":"The folder tree new documents for this scope are filed into.","operationId":"get_doc_folder_template_org_settings_docs_folders__scope__get","parameters":[{"name":"scope","in":"path","required":true,"schema":{"enum":["companies","accounts","prospects","contacts","campaigns","global"],"type":"string","description":"Which record type's folder tree. `accounts` is the canonical company template; `companies` is accepted as its synonym.","title":"Scope"},"description":"Which record type's folder tree. `accounts` is the canonical company template; `companies` is accepted as its synonym."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Organization Settings"],"summary":"Update Doc Folder Template","description":"Replace the folder tree for this scope.\n\nREPLACES. A folder missing from the body is removed from the template -\nexisting documents keep their path, but nothing new is filed there.","operationId":"update_doc_folder_template_org_settings_docs_folders__scope__put","parameters":[{"name":"scope","in":"path","required":true,"schema":{"enum":["companies","accounts","prospects","contacts","campaigns","global"],"type":"string","description":"Which record type's folder tree. `accounts` is the canonical company template; `companies` is accepted as its synonym.","title":"Scope"},"description":"Which record type's folder tree. `accounts` is the canonical company template; `companies` is accepted as its synonym."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FolderTemplateUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/settings/document-priority":{"get":{"tags":["Organization Settings"],"summary":"Get Document Priority Settings","description":"Default priority for uploaded and for AI-generated documents.\n\nPriority decides which document wins when two say different things, so\nthis is the tie-break rule the whole library is read through.","operationId":"get_document_priority_settings_org_settings_document_priority_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Organization Settings"],"summary":"Update Document Priority Settings","description":"Set the default document priorities.\n\nBOTH fields have defaults, so a partial body RESETS the one you left out.\nSend both.","operationId":"update_document_priority_settings_org_settings_document_priority_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DocumentPriorityUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/content-sources":{"get":{"tags":["Organization Settings"],"summary":"Get Content Sources","description":"The properties this organisation owns, and the channels it posts to.\n\nWhat intelligence gathering and content generation read as \"us\". The one\nsource flagged `primary` is mirrored to the org's primary website, which is\nthe domain most of Studio is generated against.","operationId":"get_content_sources_org_content_sources_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Organization Settings"],"summary":"Update Content Sources","description":"REPLACE the content sources. Anything omitted is deleted.\n\nAt most one owned source may be `primary`, and setting it moves the org's\nprimary website - which changes what future Studio documents are generated\nabout. That is the widest side effect on this route.","operationId":"update_content_sources_org_content_sources_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContentSourcesUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/settings/compliance":{"get":{"tags":["Organization Settings"],"summary":"Get Compliance Settings","description":"Which certifications this organisation claims, and the supported list.\n\nGenerated content cites these. A certification switched on here is one the\nproduct will assert to a prospect, so the write side is admin-gated twice.","operationId":"get_compliance_settings_org_settings_compliance_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Organization Settings"],"summary":"Update Compliance Settings","description":"Patch certification status, keyed by certification id.\n\nPARTIAL: only the ids you send are touched. An id the product does not\nsupport is IGNORED rather than rejected - that is the app's behaviour, so\nread the response back rather than assuming the write landed.","operationId":"update_compliance_settings_org_settings_compliance_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ComplianceSettingsUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/settings/campaign-generation":{"get":{"tags":["Organization Settings"],"summary":"Get Campaign Generation Settings","description":"Whether a new campaign auto-generates a landing page and ad images.\n\nWorth reading before `POST /campaigns`: these decide what that call\nproduces beyond the campaign itself, and both cost generation time.","operationId":"get_campaign_generation_settings_org_settings_campaign_generation_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Organization Settings"],"summary":"Update Campaign Generation Settings","description":"Set the campaign generation toggles.\n\nBOTH default to true, so an empty body turns both ON. A partial body is\nnot a partial update here.","operationId":"update_campaign_generation_settings_org_settings_campaign_generation_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CampaignGenerationUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/settings/lead-qualification":{"get":{"tags":["Organization Settings"],"summary":"Get Lead Qualification Settings","description":"Which visitor events turn into a qualified lead, and on which pages.","operationId":"get_lead_qualification_settings_org_settings_lead_qualification_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Organization Settings"],"summary":"Update Lead Qualification Settings","description":"Update lead qualification. Partial - omitted fields are left alone.\n\n`backfill=true` is the dangerous half: it walks the last 30 days of traffic\nand creates leads from every event you just switched on. Do it deliberately,\nor leave it false and use `POST .../lead-qualification/backfill` once you\nare happy with the settings.","operationId":"update_lead_qualification_settings_org_settings_lead_qualification_put","parameters":[{"name":"backfill","in":"query","required":false,"schema":{"type":"boolean","description":"Also create leads from newly-enabled events in the last 30 days. This CREATES RECORDS for traffic that already happened - it is not a dry run, and there is no undo.","default":false,"title":"Backfill"},"description":"Also create leads from newly-enabled events in the last 30 days. This CREATES RECORDS for traffic that already happened - it is not a dry run, and there is no undo."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LeadQualificationSettingsUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/settings/lead-qualification/backfill":{"post":{"tags":["Organization Settings"],"summary":"Trigger Lead Qualification Backfill","description":"Queue a backfill over every enabled signal group, last 30 days.\n\nCREATES LEAD RECORDS from traffic that already happened. Asynchronous -\npoll `GET /org/settings/lead-qualification/backfill-status` for progress.\nThe 30-day window is the app's and is not a parameter.","operationId":"trigger_lead_qualification_backfill_org_settings_lead_qualification_backfill_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/settings/lead-qualification/backfill-status":{"get":{"tags":["Organization Settings"],"summary":"Get Lead Qualification Backfill Status","description":"Progress of the backfill job for this organisation.","operationId":"get_lead_qualification_backfill_status_org_settings_lead_qualification_backfill_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/org/settings/tasks":{"get":{"tags":["Organization Settings"],"summary":"Get Task Settings","description":"Default task visibility, and the note-taking toggles beside it.","operationId":"get_task_settings_org_settings_tasks_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Organization Settings"],"summary":"Update Task Settings","description":"Set the org's default task visibility and note-taking toggles.\n\n`default_visibility` is a privilege-sensitive setting: moving it to\n`public` exposes every task created afterwards to the whole organisation.\nAdmin-gated, and the handler re-checks the role.\n\nAn EMPTY patch is refused (422) rather than no-opped, because an empty body\non this route is always a caller bug.","operationId":"update_task_settings_org_settings_tasks_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TaskSettingsUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/kb/search":{"post":{"tags":["GTM Knowledge Base"],"summary":"Search Kb","description":"Search the GTM knowledge base using full-text search.","operationId":"search_kb_kb_search_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/KBSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/kb":{"get":{"tags":["GTM Knowledge Base"],"summary":"List Kb Documents","description":"List all KB documents grouped by section.","operationId":"list_kb_documents_kb_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/schedules":{"get":{"tags":["GTM Launch Helpers"],"summary":"List sending schedules (send windows + timezone)","description":"Return the org's send-window schedules.\n\nEach row carries `id`, `name`, `timezone`, and a flattened per-day\n`windows` list. Pass `id` back as `schedule_id` on\n`POST /campaigns/{id}/launch` or `PATCH /sequences/{id}` to attach the\nschedule before the scheduler starts queueing sends.\n\nThe underlying sequencer route is `GET /schedules` (unprefixed inside the\nsequencer app); this dev-API route is a thin org-scoped proxy that\nrewraps the rows into the launch-helper DTO shape and returns a\n`{data: [...]}` envelope for consistency with the rest of the dev API.","operationId":"list_schedules_schedules_get","parameters":[{"name":"include_archived","in":"query","required":false,"schema":{"type":"boolean","description":"Include archived schedules in the response. Default False matches the sequencer schedule picker.","default":false,"title":"Include Archived"},"description":"Include archived schedules in the response. Default False matches the sequencer schedule picker."},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Substring filter on schedule name + description. Case-insensitive on the underlying SQL.","title":"Search"},"description":"Substring filter on schedule name + description. Case-insensitive on the underlying SQL."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SchedulesListResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"post":{"tags":["Sequences"],"summary":"Create Schedule","description":"Create a sending schedule: a weekly set of windows in one timezone.\n\nA day left out of `config` is a day nothing is sent. Put it on a sequence\nwith `PATCH /sequences/{id}` (`schedule_id`).","operationId":"create_schedule_schedules_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateSendingScheduleRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/event-types":{"get":{"tags":["GTM Launch Helpers"],"summary":"List bookable calendar event types (Cal.com appointments)","description":"Return the org's bookable event types (calendar links).\n\nEach row carries `id` (integer) and the booking-page metadata. Pass `id`\nback as `appointment_id` on `POST /campaigns/{id}/launch` or\n`PATCH /sequences/{id}` to wire the booking link onto a sequence so the\nCal.com short-link rewrite kicks in during send.\n\nBacked by the appointments `EventTypesHandler.handle_list` (same handler\npowering the in-app /appointments/event-types picker). We pass the\nauthenticated user through so per-user visibility rules apply identically\nto the in-app flow.","operationId":"list_event_types_event_types_get","parameters":[{"name":"include_hidden","in":"query","required":false,"schema":{"type":"boolean","description":"Include event types marked `hidden` (unbookable publicly). Default False.","default":false,"title":"Include Hidden"},"description":"Include event types marked `hidden` (unbookable publicly). Default False."},{"name":"scheduling_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by Cal.com scheduling type: managed | round_robin | collective. Omit to return all types including single-host (NULL).","title":"Scheduling Type"},"description":"Filter by Cal.com scheduling type: managed | round_robin | collective. Omit to return all types including single-host (NULL)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/EventTypesListResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/schedules/{schedule_id}":{"get":{"tags":["Sequences"],"summary":"Get Schedule","description":"One sending schedule, with its full per-day `config`.","operationId":"get_schedule_schedules__schedule_id__get","parameters":[{"name":"schedule_id","in":"path","required":true,"schema":{"type":"string","description":"Schedule id, from `GET /schedules`.","title":"Schedule Id"},"description":"Schedule id, from `GET /schedules`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Sequences"],"summary":"Update Schedule","description":"Change a schedule's name, timezone or windows. Only what you send is written.\n\nSHARED: this retimes EVERY sequence using the schedule, not one. `config`,\nwhen sent, replaces the whole week - a day omitted from it stops sending.","operationId":"update_schedule_schedules__schedule_id__patch","parameters":[{"name":"schedule_id","in":"path","required":true,"schema":{"type":"string","description":"Schedule id, from `GET /schedules`.","title":"Schedule Id"},"description":"Schedule id, from `GET /schedules`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateSendingScheduleRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/schedules/{schedule_id}/archive":{"patch":{"tags":["Sequences"],"summary":"Archive Schedule","description":"Archive or UN-archive a schedule (`is_archived` is explicit).\n\nArchived schedules drop out of `GET /schedules` unless `include_archived`\nis set. Nothing is deleted.","operationId":"archive_schedule_schedules__schedule_id__archive_patch","parameters":[{"name":"schedule_id","in":"path","required":true,"schema":{"type":"string","description":"Schedule id, from `GET /schedules`.","title":"Schedule Id"},"description":"Schedule id, from `GET /schedules`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ArchiveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequencerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/deliverability/metrics":{"get":{"tags":["GTM Deliverability"],"summary":"Get Deliverability Metrics","description":"Deliverability capacity / sends / placement / warmup for the caller's org.\n\nRead-only, org-scoped (schema = ``str(org_id).lower()``). Reuses the admin\ndashboard's capacity+sends helpers (issue #14279) and the aggregator's\nhonest placement bucketing (issue #14278) so the numbers match the internal\ndashboard by construction. Every signal fails soft to ``null`` — a missing\nClickHouse / placement source degrades the field, never the whole response.","operationId":"get_deliverability_metrics_deliverability_metrics_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":30,"minimum":1,"description":"Trailing window in days","default":7,"title":"Days"},"description":"Trailing window in days"},{"name":"mailbox_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Drill into one mailbox's slice","title":"Mailbox Id"},"description":"Drill into one mailbox's slice"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/deliverability/fleet-summary":{"get":{"tags":["Deliverability"],"summary":"Get Fleet Summary","description":"Deliverability across the whole sending fleet, in one object.\n\nCounts by health state, the fleet's inbox rate, and a single\n`safe_to_send` verdict. The right first call before a large send.","operationId":"get_fleet_summary_deliverability_fleet_summary_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/deliverability/degraded":{"get":{"tags":["Deliverability"],"summary":"List Degraded Mailboxes","description":"Mailboxes whose deliverability is in trouble, worst first.\n\n`watch` is the early warning and `paused` is the mailboxes that have\nalready been taken out of rotation. A paused mailbox still belongs to live\nsequences - see `/deliverability/sequences-health` for which.","operationId":"list_degraded_mailboxes_deliverability_degraded_get","parameters":[{"name":"min_severity","in":"query","required":false,"schema":{"type":"string","pattern":"^(watch|paused)$","description":"'watch' returns everything of concern; 'paused' only what has already stopped sending.","default":"watch","title":"Min Severity"},"description":"'watch' returns everything of concern; 'paused' only what has already stopped sending."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/deliverability/domain/{domain}/report":{"get":{"tags":["Deliverability"],"summary":"Get Domain Report","description":"One domain's deliverability: its mailboxes' health, its placement, its verdict.\n\nKeyed by domain NAME rather than by `domain_id`, matching the app - a\nreport is about the reputation of a name, which outlives any one row.","operationId":"get_domain_report_deliverability_domain__domain__report_get","parameters":[{"name":"domain","in":"path","required":true,"schema":{"type":"string","pattern":"^[A-Za-z0-9.\\-]{1,253}$","description":"Sending domain name, e.g. acme-outreach.com","title":"Domain"},"description":"Sending domain name, e.g. acme-outreach.com"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/deliverability/sequences-health":{"get":{"tags":["Deliverability"],"summary":"Get Sequences Health","description":"Live sequences that are still sending from degraded or paused mailboxes.\n\nKeyed by sequence id. These are the sequences quietly losing delivery\nright now; swapping their sender mailbox is the fix.","operationId":"get_sequences_health_deliverability_sequences_health_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/deliverability/findings":{"get":{"tags":["Deliverability"],"summary":"List Deliverability Findings","description":"Individual deliverability findings the daily routine raised, newest first.\n\nEvery filter is CLOSED to the values the lifecycle actually uses, so a\ntypo is a 422 naming them rather than a silently empty list.\n\nAn org whose schema predates the findings table gets an empty list, not an\nerror - absence of findings and absence of the table look the same here on\npurpose.","operationId":"list_deliverability_findings_deliverability_findings_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^(open|proposed|awaiting_approval|in_remediation|resolved|failed|dismissed)$"},{"type":"null"}],"description":"Filter by lifecycle state.","title":"Status"},"description":"Filter by lifecycle state."},{"name":"severity","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^(info|warn|critical)$"},{"type":"null"}],"description":"Filter by severity.","title":"Severity"},"description":"Filter by severity."},{"name":"signal","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^[a-z_]{1,30}$"},{"type":"null"}],"description":"Filter by signal name, e.g. dmarc, mailbox_health.","title":"Signal"},"description":"Filter by signal name, e.g. dmarc, mailbox_health."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Newest first. The app's own ceiling.","default":50,"title":"Limit"},"description":"Newest first. The app's own ceiling."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/deliverability/capacity-plan":{"get":{"tags":["Deliverability"],"summary":"Get Capacity Plan","description":"How much sending capacity a target volume needs, and what the shortfall costs.\n\nRECOMMENDATION ONLY. It buys nothing and holds nothing - the credit figure\nit returns is an estimate of what closing the gap WOULD cost. The buying\nis `POST /mailboxes/schedule-buy/plans`, which is a separate, deliberate\nact.","operationId":"get_capacity_plan_deliverability_capacity_plan_get","parameters":[{"name":"contacts_per_month","in":"query","required":true,"schema":{"type":"integer","maximum":100000000,"minimum":0,"description":"Volume you intend to send per month.","title":"Contacts Per Month"},"description":"Volume you intend to send per month."},{"name":"delivery_days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Days you want to spread that volume over.","default":30,"title":"Delivery Days"},"description":"Days you want to spread that volume over."},{"name":"warmed","in":"query","required":false,"schema":{"type":"boolean","description":"Assume new mailboxes must warm up before they count as capacity.","default":true,"title":"Warmed"},"description":"Assume new mailboxes must warm up before they count as capacity."},{"name":"domain_tld","in":"query","required":false,"schema":{"type":"string","pattern":"^\\.[a-z]{2,10}$","description":"Extension to price against.","default":".com","title":"Domain Tld"},"description":"Extension to price against."},{"name":"exclude_committed","in":"query","required":false,"schema":{"type":"boolean","description":"Treat the target as ADDITIONAL volume: mailboxes already in live sequences are not capacity.","default":false,"title":"Exclude Committed"},"description":"Treat the target as ADDITIONAL volume: mailboxes already in live sequences are not capacity."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/deliverability/safe-to-send":{"get":{"tags":["Deliverability"],"summary":"Get Safe To Send","description":"One verdict: can I send right now, and if not, why not.\n\nThe cheapest thing to call before a launch. A `false` here with a live\nsequence running is the signal to pause rather than to push.","operationId":"get_safe_to_send_deliverability_safe_to_send_get","parameters":[{"name":"domain","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^[A-Za-z0-9.\\-]{1,253}$"},{"type":"null"}],"description":"Limit the verdict to one domain. Omit for the whole fleet.","title":"Domain"},"description":"Limit the verdict to one domain. Omit for the whole fleet."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/deliverability/autopilot/preferences":{"get":{"tags":["Deliverability"],"summary":"Get Autopilot Preferences","description":"The org's autopilot mode, its guardrails, and what it has used this month.\n\n`guardrail_active` true means the org is in `auto` mode but has hit a\nmonthly limit, so retirements are queueing for a human again.","operationId":"get_autopilot_preferences_deliverability_autopilot_preferences_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"put":{"tags":["Deliverability"],"summary":"Set Autopilot Preferences","description":"Replace the org's autopilot preferences. `mode='auto'` AUTHORISES SPEND.\n\nIn `auto` the autopilot retires failing mailboxes and buys replacements on\nits own, without a human decision, until it has done\n`max_auto_retirements_per_month` retirements or spent\n`monthly_spend_ceiling_credits` credits this calendar month - whichever\ncomes first. Past either limit it falls back to queueing for approval for\nthe rest of the month.\n\nIn `approval` (the default) nothing is retired or bought without a person\nsaying yes, and the ceilings are inert.\n\nREPLACES all three fields; there is no partial update. Org admins and\nowners only - the app gates this the same way.","operationId":"set_autopilot_preferences_deliverability_autopilot_preferences_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AutopilotPreferencesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/deliverability/autopilot/approvals":{"get":{"tags":["Deliverability"],"summary":"List Autopilot Approvals","description":"Mailbox retirements the autopilot has queued for a person to approve.\n\nOldest first. `spare_available` says whether a warmed spare is ready to\ntake a retired mailbox's place, which is what makes approving one cheap.\nAn org whose schema predates the queue gets an empty list, not an error.","operationId":"list_autopilot_approvals_deliverability_autopilot_approvals_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/provider-domains/generate-domains":{"post":{"tags":["Provider Domains"],"summary":"Generate Domain Names","description":"Suggest buyable domain names around a keyword. SPENDS NOTHING.\n\nA naming aid, not a reservation: a name returned here can still be gone by\nthe time you buy it, so `check-availability` remains the authority.","operationId":"generate_domain_names_provider_domains_generate_domains_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DomainNameGenerateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/provider-domains/check-transfer-availability":{"post":{"tags":["Provider Domains"],"summary":"Check Transfer Availability","description":"Can this domain be transferred in, and what would it cost? SPENDS NOTHING.\n\nDifferent question from `check-availability`, which asks whether a domain\nis free to REGISTER. This one asks about a domain you already own at\nanother registrar.","operationId":"check_transfer_availability_provider_domains_check_transfer_availability_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DomainTransferAvailabilityRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/provider-domains/check-external-availability":{"post":{"tags":["Provider Domains"],"summary":"Check External Availability","description":"Can this domain be attached as an EXTERNAL sending domain? SPENDS NOTHING.\n\nExternal means graph8 never owns or bills the registration - you keep the\ndomain where it is and point its DNS here. The follow-up is\n`POST /provider-domains/add-external`.","operationId":"check_external_availability_provider_domains_check_external_availability_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ExternalDomainAvailabilityRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/provider-domains/pricing":{"get":{"tags":["Provider Domains"],"summary":"Get Sending Pricing","description":"What a mailbox and its warmup cost, in credits. SPENDS NOTHING.\n\n`credits_per_warmup_month` is the RECURRING monthly charge per mailbox\nwhile warmup is on - the number `auto-warmup` commits you to for every\nmailbox bought on a domain afterwards.","operationId":"get_sending_pricing_provider_domains_pricing_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/provider-domains/checkout-transfer":{"post":{"tags":["Provider Domains"],"summary":"Checkout Transfer Domain","description":"Transfer a domain you own elsewhere into graph8. SPENDS REAL CREDITS.\n\nThis is a purchase: it pays the registrar to move the domain and extends\nthe registration. There is no per-key spend cap, the same as the app.\n\nSend an `Idempotency-Key` header so a retry cannot pay twice. 202 means\nthe transfer was accepted and is now in the registrar's hands - it\ncompletes asynchronously and can take days. 402 if the credit hold cannot\nclear, 422 if the org's plan cannot fund a purchase at all.\n\nGet `auth_info` from your current registrar first; a wrong code fails the\ntransfer at the registrar AFTER the money has moved.","operationId":"checkout_transfer_domain_provider_domains_checkout_transfer_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DomainTransferRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/provider-domains/cancel-transfer":{"post":{"tags":["Provider Domains"],"summary":"Cancel Domain Transfer","description":"Abort an in-flight transfer.\n\nRefunds are the registrar's business, not graph8's: cancelling stops the\nmove, it does not guarantee the transfer fee back.","operationId":"cancel_domain_transfer_provider_domains_cancel_transfer_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DomainTransferCancelRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/transfer-info":{"post":{"tags":["Provider Domains"],"summary":"Get Transfer Info","description":"Where an in-flight transfer has got to. Reads only.\n\nPOST rather than GET because that is the app's own spelling, kept so the\ntwo surfaces describe one operation rather than two.","operationId":"get_transfer_info_provider_domains__domain_id__transfer_info_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/resend-transfer-password":{"post":{"tags":["Provider Domains"],"summary":"Resend Transfer Password","description":"Re-send the transfer authorisation mail to the registrant address.\n\nUse when the original never arrived. It reaches a real inbox, so it is not\na free retry loop - the registrar rate-limits it.","operationId":"resend_transfer_password_provider_domains__domain_id__resend_transfer_password_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/info":{"post":{"tags":["Provider Domains"],"summary":"Get Domain Info","description":"The registrar's record for this domain: expiry, nameservers, lock state.\n\nRead-only, and live - it asks the registrar rather than returning the last\nthing graph8 stored.","operationId":"get_domain_info_provider_domains__domain_id__info_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/external-info":{"post":{"tags":["Provider Domains"],"summary":"Get External Domain Info","description":"The DNS records an EXTERNAL domain must publish for graph8 to send from it.\n\nRead-only. Add them at whoever hosts the domain's DNS, then confirm with\n`POST /provider-domains/{domain_id}/check-propagation`.","operationId":"get_external_domain_info_provider_domains__domain_id__external_info_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/resend-verification":{"post":{"tags":["Provider Domains"],"summary":"Resend Registrant Verification","description":"Re-send the registrant verification mail.\n\nICANN suspends a domain whose registrant never verifies, which takes the\nmailboxes on it down with it. Worth calling for any domain whose\nverification status is not `Verified`.","operationId":"resend_registrant_verification_provider_domains__domain_id__resend_verification_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/forwarding":{"post":{"tags":["Provider Domains"],"summary":"Set Domain Forwarding","description":"Forward mail arriving at this domain to another address.\n\nREPLACES the current forwarding configuration rather than merging into it.","operationId":"set_domain_forwarding_provider_domains__domain_id__forwarding_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DomainForwardingRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Provider Domains"],"summary":"Delete Domain Forwarding","description":"Stop forwarding this domain's mail. Mail then lands in its own mailboxes.","operationId":"delete_domain_forwarding_provider_domains__domain_id__forwarding_delete","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/provider-status":{"post":{"tags":["Provider Domains"],"summary":"Get Provider Status","description":"How far this domain has got through managed provisioning. Reads only.\n\n`provider_status` is the connection state; the `provider_*_uid` fields are\nopaque references you may need when contacting support.","operationId":"get_provider_status_provider_domains__domain_id__provider_status_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/refresh-from-provider":{"post":{"tags":["Provider Domains"],"summary":"Refresh Domain From Provider","description":"Pull this domain's current state from the provisioning backend and store it.\n\nWrites: graph8's copy is replaced with what the provider says. Use it when\n`provider-status` looks stale against reality.","operationId":"refresh_domain_from_provider_provider_domains__domain_id__refresh_from_provider_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/regenerate-nameservers":{"post":{"tags":["Provider Domains"],"summary":"Regenerate Nameservers","description":"Mint a fresh set of nameservers for this domain.\n\nFor a domain whose propagation window expired or whose nameservers were\nchanged elsewhere. It issues NEW values - you still have to apply them,\nwith `set-nameservers` for a graph8-registered domain or at your own DNS\nhost for an external one.","operationId":"regenerate_nameservers_provider_domains__domain_id__regenerate_nameservers_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/set-nameservers":{"post":{"tags":["Provider Domains"],"summary":"Set Nameservers","description":"Point this domain's nameservers at the managed mail backend, at the registrar.\n\nOnly meaningful for a domain graph8 registered or transferred in. DNS\npropagation is not instant; confirm with `check-propagation`.","operationId":"set_nameservers_provider_domains__domain_id__set_nameservers_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/provisioning-states":{"post":{"tags":["Provider Domains"],"summary":"Get Provisioning States","description":"Live provisioning step and last error for up to 50 mailboxes. Reads only.\n\nBest-effort by design: a mailbox with no live provisioning run - finished,\nnever started, or aged out - comes back `null` rather than erroring, so\npoll this and fall back to the mailbox's own status.","operationId":"get_provisioning_states_provider_domains__domain_id__provisioning_states_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProvisioningStatesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/check-mailbox-status":{"post":{"tags":["Provider Domains"],"summary":"Check Mailbox Status","description":"Re-check one mailbox's provisioning with the provider, and record the answer.\n\nNot a pure read: a mailbox the provider now reports as ready is flipped to\nactive here, which is what makes it usable for sending.","operationId":"check_mailbox_status_provider_domains__domain_id__check_mailbox_status_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DomainMailboxRefRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/mailbox-profile-picture":{"post":{"tags":["Provider Domains"],"summary":"Update Mailbox Profile Picture","description":"Set the avatar recipients see on mail from this mailbox.\n\n`profile_picture` must be a URL the provider can fetch; it is downloaded\nserver-side, not proxied through graph8.","operationId":"update_mailbox_profile_picture_provider_domains__domain_id__mailbox_profile_picture_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MailboxProfilePictureRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/reset-password":{"post":{"tags":["Provider Domains"],"summary":"Reset Mailbox Password","description":"Replace a provider mailbox's password.\n\nAnything already signed in with the old password - including graph8's own\nsending connection until it re-reads the mailbox - stops working\nimmediately. The new password is write-only and is never returned by this\nor any other endpoint.","operationId":"reset_mailbox_password_provider_domains__domain_id__reset_password_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MailboxPasswordResetRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/delete-mailbox":{"post":{"tags":["Provider Domains"],"summary":"Delete Domain Mailbox","description":"Delete a mailbox at the provider. NOT REVERSIBLE.\n\nThe mailbox stops existing upstream and its mail goes with it. Different\nfrom `DELETE /mailboxes/{mailbox_id}`, which removes graph8's record of a\nmailbox and leaves the provider's copy alone. A domain's admin mailbox\ncannot be deleted - it is what manages the domain.\n\nTo stop paying for a purchased mailbox without destroying it, use\n`POST /mailboxes/{mailbox_id}/request-cancellation` instead.","operationId":"delete_domain_mailbox_provider_domains__domain_id__delete_mailbox_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DomainMailboxRefRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/auto-warmup":{"post":{"tags":["Provider Domains"],"summary":"Set Auto Warmup","description":"Turn automatic warmup enrolment on or off for this domain. ON COMMITS SPEND.\n\nON: every mailbox bought on this domain from now on is enrolled in warmup\nautomatically, and warmup is a RECURRING monthly credit charge per mailbox\n(`GET /provider-domains/pricing` has the figure). It is the default.\n\nOFF: new mailboxes are not enrolled and not billed for warmup. It does NOT\nstop warmup already running on existing mailboxes - use\n`POST /warmup/{mailbox_id}/disable` for that - and it does not affect\nwarmup you start by hand.","operationId":"set_auto_warmup_provider_domains__domain_id__auto_warmup_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AutoWarmupRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/provider-domains/stats":{"get":{"tags":["Provider Domains"],"summary":"Get Sending Domain Stats","description":"Counts across the org's sending domains and mailboxes. Reads only.\n\nTotals, active and external domains, provisioning progress, domains whose\nregistrant has not verified, and the warmed mailboxes that are ready for\noutreach but not yet in any live sequence. The same figures the app's\ndashboard tiles show.","operationId":"get_sending_domain_stats_provider_domains_stats_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/provider-domains/stats/mailboxes/{stat_key}":{"get":{"tags":["Provider Domains"],"summary":"List Mailboxes For Stat","description":"The mailboxes a stat counts - its result set IS that number's denominator.\n\nUse this rather than filtering `GET /mailboxes` yourself, so your list and\nthe count can never disagree about which mailboxes match.","operationId":"list_mailboxes_for_stat_provider_domains_stats_mailboxes__stat_key__get","parameters":[{"name":"stat_key","in":"path","required":true,"schema":{"const":"warmup_ready_to_outreach","type":"string","description":"Which stat to drill into","title":"Stat Key"},"description":"Which stat to drill into"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":2000,"minimum":1,"description":"Newest first. The app's own ceiling.","default":500,"title":"Limit"},"description":"Newest first. The app's own ceiling."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/mailboxes":{"get":{"tags":["Provider Domains"],"summary":"List Domain Mailboxes","description":"The mailboxes on one sending domain, a page at a time. Reads only.\n\nGET here although the app spells it POST: it changes nothing, and a read\nshould be cacheable and retryable as one.","operationId":"list_domain_mailboxes_provider_domains__domain_id__mailboxes_get","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Sending domain id (provider_domains.id) - from GET /provider-domains","title":"Domain Id"},"description":"Sending domain id (provider_domains.id) - from GET /provider-domains"},{"name":"start_row","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"First row, zero-based","default":0,"title":"Start Row"},"description":"First row, zero-based"},{"name":"end_row","in":"query","required":false,"schema":{"type":"integer","maximum":1000,"minimum":1,"description":"Row after the last one returned","default":100,"title":"End Row"},"description":"Row after the last one returned"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/provider-domains":{"get":{"tags":["Provider Domains"],"summary":"List Provider Domains","description":"List the org's sending domains.\n\nThis is the discovery route: every per-domain endpoint below needs a\n``domain_id`` from here first. Mirrors the core of the app's own\n``POST /provider-domains/fetch`` (mailbox count via a correlated\nsubquery), without its ag-grid filter/sort surface.","operationId":"list_provider_domains_provider_domains_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":20,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_List_ProviderDomainResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/provider-domains/check-availability":{"post":{"tags":["Provider Domains"],"summary":"Check Domain Availability","description":"Check whether a domain is available to buy, and its price. Spends no credits.\n\nProxies the same handler the in-app purchase wizard's first step calls.","operationId":"check_domain_availability_provider_domains_check_availability_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DomainAvailabilityCheckRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/provider-domains/checkout-purchase":{"post":{"tags":["Provider Domains"],"summary":"Checkout Purchase Domains","description":"Buy one or more sending domains. SPENDS REAL CREDITS — unrestricted, same\nas the app; there is no per-key spend cap.\n\nSend an ``Idempotency-Key`` header to make a retry safe (a repeat with the\nsame key returns the original response instead of buying twice). Returns\n402 if the credit hold can't clear, 422 if the org's plan can't fund a\npurchase at all (same gate the app UI checks), 400 for a pilot-only\nprovider or an unsupported TLD.","operationId":"checkout_purchase_domains_provider_domains_checkout_purchase_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DomainPurchaseRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/provider-domains/add-external":{"post":{"tags":["Provider Domains"],"summary":"Add External Domains","description":"Register domains you already own elsewhere for use as sending domains.\nSpends no credits — no registrar purchase happens here.","operationId":"add_external_domains_provider_domains_add_external_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AddExternalDomainsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/dns":{"post":{"tags":["Provider Domains"],"summary":"Set Dns Records","description":"Set (or reset to default) the sending DNS records for a domain.","operationId":"set_dns_records_provider_domains__domain_id__dns_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Provider domain ID (provider_domains.id) — from GET /provider-domains","title":"Domain Id"},"description":"Provider domain ID (provider_domains.id) — from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DnsRecordsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/checkout-mailboxes":{"post":{"tags":["Provider Domains"],"summary":"Checkout Purchase Mailboxes","description":"Buy one or more mailboxes on a domain. SPENDS REAL CREDITS — unrestricted,\nsame as the app; there is no per-key spend cap.\n\nSend an ``Idempotency-Key`` header to make a retry safe. Returns 402 if\nthe credit hold can't clear, 422 if the org's plan can't fund a purchase\nat all, 400 for an unconnected/wrong-platform domain, too many mailboxes,\nor a missing username, 404 if ``domain_id`` doesn't belong to this org.","operationId":"checkout_purchase_mailboxes_provider_domains__domain_id__checkout_mailboxes_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Provider domain ID (provider_domains.id) — from GET /provider-domains","title":"Domain Id"},"description":"Provider domain ID (provider_domains.id) — from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MailboxPurchaseRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/connect-provider":{"post":{"tags":["Provider Domains"],"summary":"Connect Provider","description":"Connect a purchased domain to the managed mailbox-provisioning backend.\n\nRequired once per domain before ``checkout-mailboxes`` will succeed for a\nmanaged (``provider='managed'``) purchase — an unconnected domain 400s\nthere with an actionable message pointing back here.","operationId":"connect_provider_provider_domains__domain_id__connect_provider_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Provider domain ID (provider_domains.id) — from GET /provider-domains","title":"Domain Id"},"description":"Provider domain ID (provider_domains.id) — from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/provider-domains/{domain_id}/check-propagation":{"post":{"tags":["Provider Domains"],"summary":"Check Domain Propagation","description":"Check whether a connected domain's nameservers have propagated yet.","operationId":"check_domain_propagation_provider_domains__domain_id__check_propagation_post","parameters":[{"name":"domain_id","in":"path","required":true,"schema":{"type":"integer","description":"Provider domain ID (provider_domains.id) — from GET /provider-domains","title":"Domain Id"},"description":"Provider domain ID (provider_domains.id) — from GET /provider-domains"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/channels/preferences":{"get":{"tags":["Channels"],"summary":"Get Channel Preferences","description":"Every org-wide channel preference, with defaults already applied.\n\nA key that is missing from the org's stored settings still appears here\ncarrying its default, so this is the complete list of what\n`PUT /channels/preferences` will accept - there is no separate schema\nendpoint to look one up in.\n\nNeeds a personal API key whose user can read channel preferences.","operationId":"get_channel_preferences_channels_preferences_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"put":{"tags":["Channels"],"summary":"Set Channel Preference","description":"Set ONE preference. Everything else is left alone.\n\nPUT of a single key/value pair rather than the whole object, matching the\napp: sending the full set would make a stale read overwrite a change\nsomeone else made between your GET and your PUT.\n\n`key` must be one `GET /channels/preferences` returned, and `value` must\nbe a shape that key accepts - anything else is a 422 saying which.\n\nThese are org-wide compliance switches. Needs a personal API key whose\nuser can write channel preferences; org admins and owners always can.","operationId":"set_channel_preference_channels_preferences_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ChannelPreferenceRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/sms/phone-numbers":{"get":{"tags":["Channels"],"summary":"List Sms Phone Numbers","description":"The org's SMS numbers, each with its AI-inbox settings merged on.\n\n`enabled_only=true` narrows to the numbers whose conversations reach the\ninbox. A number with no stored settings still appears, carrying the\ndefaults, so absence from this list means the number is not the org's -\nnot that it is unconfigured.","operationId":"list_sms_phone_numbers_sms_phone_numbers_get","parameters":[{"name":"enabled_only","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Enabled Only"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/sms/phone-numbers/{phone_number}/config":{"get":{"tags":["Channels"],"summary":"Get Sms Phone Config","description":"One number's stored AI-inbox settings.\n\n404 when the number has never been configured - it is then running on the\ndefaults `GET /sms/phone-numbers` shows for it.","operationId":"get_sms_phone_config_sms_phone_numbers__phone_number__config_get","parameters":[{"name":"phone_number","in":"path","required":true,"schema":{"type":"string","description":"Phone number in E.164 form, e.g. +15551234567","title":"Phone Number"},"description":"Phone number in E.164 form, e.g. +15551234567"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/sms/phone-numbers/{phone_number}":{"put":{"tags":["Channels"],"summary":"Update Sms Phone Config","description":"Change one number's AI-inbox settings. Omitted fields are left alone.\n\n`ai_inbox_enabled` decides whether the number's conversations appear in\nthe inbox at all. `auto_respond` decides whether the AI REPLIES on it\nwithout a human - turning that on puts generated messages in front of real\npeople, so it is the consequential one of the two.\n\nA PATCH in PUT's clothing, matching the app rather than inventing a second\nspelling for the same operation.","operationId":"update_sms_phone_config_sms_phone_numbers__phone_number__put","parameters":[{"name":"phone_number","in":"path","required":true,"schema":{"type":"string","description":"Phone number in E.164 form, e.g. +15551234567","title":"Phone Number"},"description":"Phone number in E.164 form, e.g. +15551234567"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SmsPhoneConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxDomainPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/appointments/availability/team":{"get":{"tags":["Appointments"],"summary":"List Team Availability","description":"Every teammate's availability windows for one day.\n\nCursor-paged on user id rather than offset, so a team that changes between\npages does not shift rows under you. An empty `date_ranges` means that\nperson has not set up a schedule, not that they are fully booked.","operationId":"list_team_availability_appointments_availability_team_get","parameters":[{"name":"date","in":"query","required":true,"schema":{"type":"string","pattern":"^\\d{4}-\\d{2}-\\d{2}$","description":"The day, `YYYY-MM-DD`.","title":"Date"},"description":"The day, `YYYY-MM-DD`."},{"name":"viewer_tz","in":"query","required":false,"schema":{"type":"string","description":"IANA timezone. INFORMATIONAL - the windows come back in UTC and the caller renders them; this shifts nothing server-side.","default":"UTC","title":"Viewer Tz"},"description":"IANA timezone. INFORMATIONAL - the windows come back in UTC and the caller renders them; this shifts nothing server-side."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":50,"title":"Limit"}},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"`next_cursor` from the previous page.","title":"Cursor"},"description":"`next_cursor` from the previous page."},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Name or email substring.","title":"Search"},"description":"Name or email substring."},{"name":"user_ids","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"integer"}},{"type":"null"}],"description":"Only these teammates. REPEATABLE (`?user_ids=1&user_ids=2`), and it takes PRECEDENCE over `search` - sending both ignores the search.","title":"User Ids"},"description":"Only these teammates. REPEATABLE (`?user_ids=1&user_ids=2`), and it takes PRECEDENCE over `search` - sending both ignores the search."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/calendars/events":{"get":{"tags":["Appointments"],"summary":"List Calendar Events","description":"What is already on the connected Google / Outlook calendars in a window.\n\nThis is what makes a slot unavailable, so it is the read to reach for when\navailability looks wrong. READ-ONLY and display-only: private events come\nback as \"Busy\" blocks, and a calendar that fails to load is reported in\n`errors` rather than failing the request.","operationId":"list_calendar_events_appointments_calendars_events_get","parameters":[{"name":"start","in":"query","required":true,"schema":{"type":"string","format":"date-time","description":"Window start, ISO-8601.","title":"Start"},"description":"Window start, ISO-8601."},{"name":"end","in":"query","required":true,"schema":{"type":"string","format":"date-time","description":"Window end, ISO-8601.","title":"End"},"description":"Window end, ISO-8601."},{"name":"scope","in":"query","required":false,"schema":{"enum":["my","org"],"type":"string","description":"`my` for the key owner alone, `org` for every member who has not opted out. An empty `org` result means nobody shares a calendar, not that nobody is busy.","default":"my","title":"Scope"},"description":"`my` for the key owner alone, `org` for every member who has not opted out. An empty `org` result means nobody shares a calendar, not that nobody is busy."},{"name":"host_emails","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"CSV. Narrows `org` scope to these members.","title":"Host Emails"},"description":"CSV. Narrows `org` scope to these members."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/bookings/import":{"post":{"tags":["Appointments"],"summary":"Import Meeting","description":"Pull a meeting booked OUTSIDE graph8 into the bookings list.\n\nFor the meeting somebody put straight into their calendar. The event must\nbe on a calendar the key owner connected; its details are re-read from\nthere. IDEMPOTENT: importing the same event twice returns the first\nbooking rather than creating a second.","operationId":"import_meeting_appointments_bookings_import_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ImportMeetingRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"}},"/appointments/bookings/insights/export":{"get":{"tags":["Appointments"],"summary":"Export Booking Insights","description":"The bookings behind `GET /appointments/bookings/insights`, one row each, as CSV.\n\nAn Admin key sees the team (or `member_user_id`'s); anyone else sees their\nown bookings only - the same split the insights read makes.","operationId":"export_booking_insights_appointments_bookings_insights_export_get","parameters":[{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO date. Omit for all time.","title":"Date From"},"description":"ISO date. Omit for all time."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO date. Omit for all time.","title":"Date To"},"description":"ISO date. Omit for all time."},{"name":"event_type_ids","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^\\s*\\d+\\s*(,\\s*\\d+\\s*)*$"},{"type":"null"}],"description":"CSV of INTEGER event type ids. Checked here because the app splits and `int()`s it unguarded.","title":"Event Type Ids"},"description":"CSV of INTEGER event type ids. Checked here because the app splits and `int()`s it unguarded."},{"name":"member_user_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"One member's bookings. Honoured for Admin keys only.","title":"Member User Id"},"description":"One member's bookings. Honoured for Admin keys only."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CsvExportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/bookings/sequences-picker":{"get":{"tags":["Appointments"],"summary":"List Sequences For Picker","description":"Sequences a booking can be attributed to (`PATCH .../bookings/{uid}/sequence`).\n\nSCOPED by the same sequence visibility the sequencer list uses, so two\nkeys can legitimately get different lists. Archived and draft sequences\nare left out.","operationId":"list_sequences_for_picker_appointments_bookings_sequences_picker_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/routing-forms/{form_id}/responses/export":{"get":{"tags":["Appointments"],"summary":"Export Routing Form Responses","description":"Every response to a routing form, as CSV - one column per field.\n\nThe paged JSON read is `GET /appointments/routing-forms/{id}/responses`.\nCapped at the app's 10,000 most recent responses. A form you cannot see\nis a 404, not a 403, so its existence is not disclosed.","operationId":"export_routing_form_responses_appointments_routing_forms__form_id__responses_export_get","parameters":[{"name":"form_id","in":"path","required":true,"schema":{"type":"integer","description":"Routing form id.","title":"Form Id"},"description":"Routing form id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CsvExportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/saved-filters":{"get":{"tags":["Appointments"],"summary":"List Saved Filters","description":"The caller's saved views over the bookings list.","operationId":"list_saved_filters_appointments_saved_filters_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"},"post":{"tags":["Appointments"],"summary":"Create Saved Filter","description":"Save a view. A second view with the same title is a 409.\n\n`state` is the filter itself and is round-tripped as-is.","operationId":"create_saved_filter_appointments_saved_filters_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateSavedFilterRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/appointments/saved-filters/{filter_id}":{"put":{"tags":["Appointments"],"summary":"Update Saved Filter","description":"Change a saved view.\n\n`null` LEAVES A FIELD ALONE, except `description`, where null is a real\nclear. That asymmetry is the app's and is mirrored rather than smoothed\nover, because smoothing it would make \"remove the description\" impossible.","operationId":"update_saved_filter_appointments_saved_filters__filter_id__put","parameters":[{"name":"filter_id","in":"path","required":true,"schema":{"type":"string","description":"Filter id (UUID).","title":"Filter Id"},"description":"Filter id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateSavedFilterRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Appointments"],"summary":"Delete Saved Filter","description":"Delete a saved view. The bookings it selected are untouched.\n\nAlways a success, whether or not the id existed - the app does not\ndisclose which filters exist, and this does not either.","operationId":"delete_saved_filter_appointments_saved_filters__filter_id__delete","parameters":[{"name":"filter_id","in":"path","required":true,"schema":{"type":"string","description":"Filter id (UUID).","title":"Filter Id"},"description":"Filter id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/appointments/membership":{"get":{"tags":["Appointments"],"summary":"List Membership","description":"Everyone in the organisation, as scheduling sees them.\n\nThe source of the integer `user_id` the member and role routes take.","operationId":"list_membership_appointments_membership_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/membership/by-user/{user_id}/role":{"patch":{"tags":["Appointments"],"summary":"Update Member Role","description":"Change someone's SCHEDULING role. Admin keys only.\n\nThis decides what they can do in scheduling, not in graph8 generally -\norganisation roles live in Settings and are not reachable from here.","operationId":"update_member_role_appointments_membership_by_user__user_id__role_patch","parameters":[{"name":"user_id","in":"path","required":true,"schema":{"type":"integer","description":"The member's INTEGER scheduling user id - `user_id` from `GET /appointments/membership`. Not a PropelAuth id or an email.","title":"User Id"},"description":"The member's INTEGER scheduling user id - `user_id` from `GET /appointments/membership`. Not a PropelAuth id or an email."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateMemberRoleRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/appointments/org-settings":{"get":{"tags":["Appointments"],"summary":"Get Org Settings","description":"The branding the public booking page wears, defaults filled in.","operationId":"get_org_settings_appointments_org_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Appointments"],"summary":"Update Org Settings","description":"Change the booking page's branding. Admin keys only.\n\nOnly what you send is written. This is what a PROSPECT sees, so a wrong\nvalue here is visible outside the organisation rather than inside it.","operationId":"update_org_settings_appointments_org_settings_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateOrgSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/appointments/event-types/{event_type_id}/members/all":{"post":{"tags":["Appointments"],"summary":"Assign All Members","description":"Give EVERY active member their own bookable copy of a managed template.\n\nIdempotent - members who already have a copy are skipped.\n`include_future_joiners` is a standing rule: leave it true and someone who\njoins next month gets a copy without anyone running this again.","operationId":"assign_all_members_appointments_event_types__event_type_id__members_all_post","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BulkAssignMembersRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/appointments/event-types/{event_type_id}/members":{"post":{"tags":["Appointments"],"summary":"Assign Managed Member","description":"Give ONE member their own bookable copy of a managed template.\n\nThe template itself is not bookable - it distributes a child event type\nper member, which is what that member's booking link points at.","operationId":"assign_managed_member_appointments_event_types__event_type_id__members_post","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssignManagedMemberRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/appointments/event-types/{event_type_id}/members/{user_id}":{"delete":{"tags":["Appointments"],"summary":"Unassign Managed Member","description":"Take a member off a managed template.\n\nDESTRUCTIVE in a way the name understates: this HARD-DELETES that member's\nchild event type, so their booking link for it stops resolving. Bookings\nalready made survive, detached from any event type.","operationId":"unassign_managed_member_appointments_event_types__event_type_id__members__user_id__delete","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"user_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"The member's integer scheduling user id.","title":"User Id"},"description":"The member's integer scheduling user id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/appointments/event-types/{event_type_id}/locked-fields":{"put":{"tags":["Appointments"],"summary":"Set Locked Fields","description":"Decide which fields a managed template owns for every child copy.\n\nA locked field is read-only on the child AND is re-propagated from the\ntemplate - so locking `length` after the fact OVERWRITES whatever each\nmember had set. `propagation_notice` in the result counts the future\nbookings that touched. An empty list unlocks everything.","operationId":"set_locked_fields_appointments_event_types__event_type_id__locked_fields_put","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetLockedFieldsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/appointments/event-types/{event_type_id}/destination-calendar":{"get":{"tags":["Appointments"],"summary":"Get Event Type Destination Calendar","description":"Where bookings for THIS event type are written.\n\nThe per-event-type OVERRIDE of `GET /appointments/calendars/destination`.\nNull fields mean no override is set and the account default applies.","operationId":"get_event_type_destination_calendar_appointments_event_types__event_type_id__destination_calendar_get","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"},"put":{"tags":["Appointments"],"summary":"Set Event Type Destination Calendar","description":"Point one event type at a specific calendar.\n\nThe credential must belong to the key owner - the app enforces that, which\nis why this cannot write bookings onto a colleague's calendar.","operationId":"set_event_type_destination_calendar_appointments_event_types__event_type_id__destination_calendar_put","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateDestinationCalendarRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Appointments"],"summary":"Clear Event Type Destination Calendar","description":"Drop the per-event-type override. The ACCOUNT default is untouched, so\nbookings fall back to it rather than stopping.","operationId":"clear_event_type_destination_calendar_appointments_event_types__event_type_id__destination_calendar_delete","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/appointments/event-types/{event_type_id}/selected-calendars":{"get":{"tags":["Appointments"],"summary":"Get Event Type Selected Calendars","description":"Which calendars are checked for conflicts on this event type.\n\nThe read to reach for when a slot was offered that should not have been:\na calendar missing from here is a calendar nobody checked.","operationId":"get_event_type_selected_calendars_appointments_event_types__event_type_id__selected_calendars_get","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"},"put":{"tags":["Appointments"],"summary":"Set Event Type Selected Calendars","description":"Set the conflict-check scope for this event type.\n\n`scope=\"account\"` falls back to the key owner's account-wide selection\nand IGNORES `entries`. `scope=\"event_type\"` REPLACES the per-event-type\nlist with the entries sent (only `enabled` ones are kept) - so an empty\nlist there means nothing is checked and every slot looks free.","operationId":"set_event_type_selected_calendars_appointments_event_types__event_type_id__selected_calendars_put","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateSelectedCalendarsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/appointments/event-types/{event_type_id}/embed":{"get":{"tags":["Appointments"],"summary":"Get Embed Config","description":"How the embedded booking widget for this event type is styled.\n\nHosts of the event type and Admin keys only.","operationId":"get_embed_config_appointments_event_types__event_type_id__embed_get","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Appointments"],"summary":"Update Embed Config","description":"Restyle the embedded booking widget. Only what you send is written.\n\nLike the org branding, this is visible to PROSPECTS rather than the team.","operationId":"update_embed_config_appointments_event_types__event_type_id__embed_patch","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateEmbedConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/appointments/slots":{"get":{"tags":["Appointments"],"summary":"Get Available Slots","description":"The bookable times for an event type, grouped by date under `slots`.\n\nThe AUTHENTICATED slots read - the unauthenticated one a prospect's browser\ncalls is deliberately not published (see the module docstring).","operationId":"get_available_slots_appointments_slots_get","parameters":[{"name":"event_type_id","in":"query","required":true,"schema":{"type":"integer","description":"Event type to compute slots for.","title":"Event Type Id"},"description":"Event type to compute slots for."},{"name":"start","in":"query","required":true,"schema":{"type":"string","description":"Window start, ISO-8601. A bare date is read as UTC.","title":"Start"},"description":"Window start, ISO-8601. A bare date is read as UTC."},{"name":"end","in":"query","required":true,"schema":{"type":"string","description":"Window end, ISO-8601. At most 60 days after `start`.","title":"End"},"description":"Window end, ISO-8601. At most 60 days after `start`."},{"name":"time_zone","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"IANA timezone to express the slots in.","title":"Time Zone"},"description":"IANA timezone to express the slots in."},{"name":"duration","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Minutes, for a multi-duration event type. Omit for its own length.","title":"Duration"},"description":"Minutes, for a multi-duration event type. Omit for its own length."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/slots/reserve":{"post":{"tags":["Appointments"],"summary":"Reserve Slot","description":"Hold a slot for ten minutes while a booker fills in the form.\n\nNOT a booking: nothing is written to a calendar and nobody is notified.\nThe hold lapses by itself at `release_at`; release it explicitly if you\nknow the booker walked away. A slot already taken is a 409.","operationId":"reserve_slot_appointments_slots_reserve_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ReserveSlotRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/appointments/slots/reserve/{slot_uid}":{"delete":{"tags":["Appointments"],"summary":"Release Slot","description":"Give a held slot back before its hold lapses. Only the holder can.","operationId":"release_slot_appointments_slots_reserve__slot_uid__delete","parameters":[{"name":"slot_uid","in":"path","required":true,"schema":{"type":"string","description":"The `uid` returned by `POST /appointments/slots/reserve`.","title":"Slot Uid"},"description":"The `uid` returned by `POST /appointments/slots/reserve`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/appointments/profile":{"get":{"tags":["Appointments"],"summary":"Get Schedule Profile","description":"The scheduling profile of the person who minted this key.\n\nPublished as `/profile` rather than the app's `/me`: an organisation key\nhas no person behind it, so `/me` would promise something it cannot give.\nThe first read seeds the profile with defaults if it does not exist yet.","operationId":"get_schedule_profile_appointments_profile_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Appointments"],"summary":"Update Schedule Profile","description":"Change the key owner's scheduling preferences. Only what you send is written.\n\n`username` is the personal booking-URL slug and is GLOBALLY unique across\ngraph8, claimed atomically - a rename can lose the race and come back as a\nconflict rather than succeeding quietly.","operationId":"update_schedule_profile_appointments_profile_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateScheduleProfileRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SchedulingPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/appointments/bookings/insights":{"get":{"tags":["Appointments"],"summary":"Get aggregated booking insights","description":"Return aggregated booking insights for the caller's org.\n\nCovers booking counts, show/no-show rates, and per-event-type breakdowns\nfor the given date window.  Backed by ``BookingsHandler.handle_insights``\n(same handler as the in-app insights view).  ``is_admin`` is forced False\nso the caller sees only their own data. The in-app ``member_user_id`` filter\nis intentionally NOT exposed: it is an admin-only knob and an API key never\nholds admin, so the handler would ignore it anyway - omitting it from the\nroute signature avoids the misleading \"forwarded but ignored\" surface.","operationId":"get_booking_insights_appointments_bookings_insights_get","parameters":[{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO date string for range start (e.g. '2026-01-01').","title":"Date From"},"description":"ISO date string for range start (e.g. '2026-01-01')."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO date string for range end (e.g. '2026-12-31').","title":"Date To"},"description":"ISO date string for range end (e.g. '2026-12-31')."},{"name":"event_type_ids","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated event-type IDs to filter by.","title":"Event Type Ids"},"description":"Comma-separated event-type IDs to filter by."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Get Booking Insights Appointments Bookings Insights Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/bookings/{booking_uid}/confirm":{"post":{"tags":["Appointments"],"summary":"Confirm or reject a pending booking","description":"Confirm or reject a booking that requires host approval.\n\nWhen ``confirmed=True`` the booking moves from ``pending`` to\n``accepted`` and confirmation emails are sent.  When ``confirmed=False``\nthe booking is rejected and the attendee is notified with the optional\n``reason``.  Backed by ``BookingsHandler.handle_confirm``; raises 404\nwhen the booking uid is not visible to the caller, 403 on permission.","operationId":"confirm_booking_appointments_bookings__booking_uid__confirm_post","parameters":[{"name":"booking_uid","in":"path","required":true,"schema":{"type":"string","description":"Booking UID (uuid string).","title":"Booking Uid"},"description":"Booking UID (uuid string)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ConfirmBookingRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Confirm Booking Appointments Bookings  Booking Uid  Confirm Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"}},"/appointments/bookings/{booking_uid}/mark-absent":{"post":{"tags":["Appointments"],"summary":"Mark host or attendees as no-show","description":"Record a no-show for the host, one or more attendees, or both.\n\nPass ``host=true`` to flag the host as absent.  Pass ``attendees`` as a\nlist of attendee dicts (each containing at least ``email``) to flag\nspecific attendees.  Backed by ``BookingsHandler.handle_mark_absent``\n(updates ``no_show`` flags; sends no automatic notifications - this is\nan operator CRM action).  Raises 404 when the booking uid is not visible\nto the caller.","operationId":"mark_absent_appointments_bookings__booking_uid__mark_absent_post","parameters":[{"name":"booking_uid","in":"path","required":true,"schema":{"type":"string","description":"Booking UID (uuid string).","title":"Booking Uid"},"description":"Booking UID (uuid string)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MarkAbsentRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Mark Absent Appointments Bookings  Booking Uid  Mark Absent Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"}},"/appointments/bookings/{booking_uid}/location":{"patch":{"tags":["Appointments"],"summary":"Change a booking's location and/or conferencing","description":"Change a booking's physical location and/or its conferencing.\n\nTwo independent fields; send only the one you change. An omitted field is\nleft as is, and ``null`` clears it:\n\n* ``selected_location``: a location object, e.g.\n  ``{\"kind\": \"in_person_host\", \"address\": \"1 Market St\"}``,\n  ``{\"kind\": \"phone_host\", \"phone\": \"+14155550100\"}`` or\n  ``{\"kind\": \"custom\", \"display_label\": \"Lobby\"}``.\n* ``selected_conferencing``: ``{\"kind\": \"link\", \"link\": \"https://...\"}`` for a\n  meeting URL, or ``{\"kind\": \"conferencing\", \"provider\": \"zoom\"}`` (also\n  ``roam_auto``, ``ms_teams``, ``google_meet``), which creates a NEW meeting room.\n* ``notify_attendees`` (default true): the host is always emailed.\n\nThe host's calendar event is updated too; ``calendar_synced`` in the response\nis false when that update failed (the change is saved either way). Errors:\n404 when the booking is not visible to the caller, 409 when it is cancelled,\npast, imported or changed meanwhile, 422 for an invalid value or a provider\nthe host has not connected, 429 past the per-booking edit limit, 502 when a\nnew meeting room could not be created (nothing is changed then).","operationId":"update_booking_location_appointments_bookings__booking_uid__location_patch","parameters":[{"name":"booking_uid","in":"path","required":true,"schema":{"type":"string","description":"Booking UID (uuid string).","title":"Booking Uid"},"description":"Booking UID (uuid string)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateLocationRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Update Booking Location Appointments Bookings  Booking Uid  Location Patch"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"}},"/appointments/bookings/{booking_uid}/request-reschedule":{"post":{"tags":["Appointments"],"summary":"Send a reschedule-request email to the attendee (host action)","description":"Ask the attendee to pick a new time.\n\nSends a reschedule-request email with the optional host ``reason``\nmessage and a link to the public booking page.  Does NOT move or cancel\nthe original booking - the attendee reschedules by clicking the link.\nBacked by ``BookingsHandler.handle_request_reschedule``.  Raises 404\nwhen the booking uid is not visible to the caller.","operationId":"request_booking_reschedule_appointments_bookings__booking_uid__request_reschedule_post","parameters":[{"name":"booking_uid","in":"path","required":true,"schema":{"type":"string","description":"Booking UID (uuid string).","title":"Booking Uid"},"description":"Booking UID (uuid string)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RequestRescheduleRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Request Booking Reschedule Appointments Bookings  Booking Uid  Request Reschedule Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"}},"/appointments/bookings/{booking_uid}/guests":{"post":{"tags":["Appointments"],"summary":"Add guest attendees to a booking","description":"Invite additional guests (email addresses) to an existing booking.\n\nSends notification emails to each new guest and updates the booking's\nattendee list.  Backed by ``BookingsHandler.handle_add_guests``.\nRaises 404 when the booking uid is not visible to the caller.","operationId":"add_booking_guests_appointments_bookings__booking_uid__guests_post","parameters":[{"name":"booking_uid","in":"path","required":true,"schema":{"type":"string","description":"Booking UID (uuid string).","title":"Booking Uid"},"description":"Booking UID (uuid string)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AddGuestsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Add Booking Guests Appointments Bookings  Booking Uid  Guests Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"}},"/appointments/bookings/{booking_uid}/notes":{"post":{"tags":["Appointments"],"summary":"Add an internal note to a booking","description":"Append an internal (host-only) note to a booking.\n\nNotes are not visible to attendees; they appear in the booking detail\nview for org members.  Backed by ``BookingsHandler.handle_add_note``.\nRaises 404 when the booking uid is not visible to the caller.","operationId":"add_booking_note_appointments_bookings__booking_uid__notes_post","parameters":[{"name":"booking_uid","in":"path","required":true,"schema":{"type":"string","description":"Booking UID (uuid string).","title":"Booking Uid"},"description":"Booking UID (uuid string)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AddNoteRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Add Booking Note Appointments Bookings  Booking Uid  Notes Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"}},"/appointments/bookings/{booking_uid}/sequence":{"patch":{"tags":["Appointments"],"summary":"Associate a booking with a sequence (or detach)","description":"Link a booking to a sequencer sequence or remove the link.\n\n``sequence_id`` is the sequence UUID (``seqsequences.id``); pass\n``null`` / omit to detach.  Writes to\n``booking.metadata_['campaignId']`` - the same field the public booking\nflow populates from ``?campaignId=`` at create time.  No EDA event is\nemitted (CRM-only action).  Backed by\n``BookingsHandler.handle_update_sequence``.  Raises 404 when the\nbooking uid is not visible to the caller.","operationId":"update_booking_sequence_appointments_bookings__booking_uid__sequence_patch","parameters":[{"name":"booking_uid","in":"path","required":true,"schema":{"type":"string","description":"Booking UID (uuid string).","title":"Booking Uid"},"description":"Booking UID (uuid string)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/appointments__domain__entities__UpdateSequenceRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Update Booking Sequence Appointments Bookings  Booking Uid  Sequence Patch"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"}},"/appointments/event-types/{event_type_id}":{"get":{"tags":["Appointments"],"summary":"Get full detail for one bookable event type","description":"Return the full event-type record (booking fields, locations, hosts,\nschedule, buffers, notice) — everything an agent needs before booking a\nslot. Backed by ``EventTypesHandler.handle_get`` (same handler as the\nin-app event-type detail view). Raises 404 when the id doesn't exist in\nthis org.","operationId":"get_event_type_appointments_event_types__event_type_id__get","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Event-type integer ID.","title":"Event Type Id"},"description":"Event-type integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Get Event Type Appointments Event Types  Event Type Id  Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Appointments"],"summary":"Update an event type (partial)","description":"Partially update an event type. Only the fields you send are changed\n(``exclude_unset`` semantics) - omit a field to leave it untouched, including\n``hidden`` (the active/visible toggle). Reuses\n``EventTypesHandler.handle_update`` (schedule-ownership guard, host policy).\n``is_admin`` is forced False.","operationId":"update_event_type_appointments_event_types__event_type_id__patch","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Event-type integer ID.","title":"Event Type Id"},"description":"Event-type integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateEventTypeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Update Event Type Appointments Event Types  Event Type Id  Patch"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Appointments"],"summary":"Delete an event type","description":"Delete an event type. Reuses ``EventTypesHandler.handle_delete``.\n\n``EventTypePolicy.can_delete()`` is ADMIN-ONLY (Cal.com \"team event delete =\nadmin only\"; hosts cannot delete). So this requires the API key's user to\nhold Admin/Owner in the org - resolved via ``_is_org_admin``. Member/Viewer\nkeys and org-scoped machine keys get a 403 from the handler. Returns\n``{data: {deleted: true, event_type_id}}`` on success.","operationId":"delete_event_type_appointments_event_types__event_type_id__delete","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Event-type integer ID.","title":"Event Type Id"},"description":"Event-type integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Delete Event Type Appointments Event Types  Event Type Id  Delete"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/appointments/bookings":{"get":{"tags":["Appointments"],"summary":"List the caller's bookings (paginated)","description":"List bookings visible to the caller.\n\nPersonal keys retain the member-scoped path. An organization key that\npassed the existing explicit ``meetings:read`` gate uses the handler's\norg-wide read path and therefore never looks up the synthetic API identity.","operationId":"list_bookings_appointments_bookings_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by status: accepted | pending | cancelled | rejected.","title":"Status"},"description":"Filter by status: accepted | pending | cancelled | rejected."},{"name":"event_type_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Only bookings for this event type.","title":"Event Type Id"},"description":"Only bookings for this event type."},{"name":"after_start","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO-8601 lower bound on start_time.","title":"After Start"},"description":"ISO-8601 lower bound on start_time."},{"name":"before_end","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO-8601 upper bound on end_time.","title":"Before End"},"description":"ISO-8601 upper bound on end_time."},{"name":"attendee_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by an attendee email.","title":"Attendee Email"},"description":"Filter by an attendee email."},{"name":"sort_by","in":"query","required":false,"schema":{"type":"string","description":"start_time | end_time | created_at | status.","default":"start_time","title":"Sort By"},"description":"start_time | end_time | created_at | status."},{"name":"sort_order","in":"query","required":false,"schema":{"type":"string","pattern":"^(asc|desc)$","default":"desc","title":"Sort Order"}},{"name":"skip","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Skip"}},{"name":"take","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":20,"title":"Take"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Bookings Appointments Bookings Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"},"post":{"tags":["Appointments"],"summary":"Create a booking (charges credits + sends notifications)","description":"Create (book) an appointment on behalf of the API key's user.\n\nReuses ``BookingsHandler.handle_create`` verbatim — same host selection,\nconflict checks, credit charge (~20 credits), calendar push, attendee\nnotifications, and EDA emit as an in-app booking. Surfaces the handler's\n402 (insufficient credits) / 409 (slot conflict) / 404 (event type)\nuntouched.","operationId":"create_booking_appointments_bookings_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateBookingRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Create Booking Appointments Bookings Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"}},"/appointments/bookings/{booking_uid}":{"get":{"tags":["Appointments"],"summary":"Get a single booking by UID","description":"Return the full booking detail (attendees, references, meeting_url,\nresponses, internal notes). Backed by ``BookingsHandler.handle_get``;\nraises 404 when the UID isn't visible to the caller.","operationId":"get_booking_appointments_bookings__booking_uid__get","parameters":[{"name":"booking_uid","in":"path","required":true,"schema":{"type":"string","description":"Booking UID (uuid string).","title":"Booking Uid"},"description":"Booking UID (uuid string)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Get Booking Appointments Bookings  Booking Uid  Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/bookings/{booking_uid}/cancel":{"post":{"tags":["Appointments"],"summary":"Cancel a booking and notify both parties","description":"Cancel a booking. Reuses ``BookingsHandler.handle_cancel`` (sends the\ncancellation emails, releases the slot, emits the EDA event). Body is\noptional — omit it to cancel with no reason.","operationId":"cancel_booking_appointments_bookings__booking_uid__cancel_post","parameters":[{"name":"booking_uid","in":"path","required":true,"schema":{"type":"string","title":"Booking Uid"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/CancelBookingRequest"},{"type":"null"}],"title":"Request"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Cancel Booking Appointments Bookings  Booking Uid  Cancel Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/appointments/bookings/{booking_uid}/reschedule":{"post":{"tags":["Appointments"],"summary":"Reschedule a booking to a new start time","description":"Reschedule a booking to ``start_time``. Reuses\n``BookingsHandler.handle_reschedule`` (no double credit charge — reschedules\nare free; re-renders the title, updates the calendar event, notifies\nattendees). Returns the NEW booking detail.","operationId":"reschedule_booking_appointments_bookings__booking_uid__reschedule_post","parameters":[{"name":"booking_uid","in":"path","required":true,"schema":{"type":"string","title":"Booking Uid"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RescheduleBookingRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Reschedule Booking Appointments Bookings  Booking Uid  Reschedule Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"}},"/appointments/event-types/{event_type_id}/hosts":{"post":{"tags":["Appointments"],"summary":"Add Event Type Host","description":"Add a host to an event type.\n\n`is_fixed` is the round-robin distinction that matters: a FIXED host is on\nevery booking, a non-fixed host is one of the rotation. Getting it wrong\nsilently changes who gets booked, so it is declared rather than defaulted\ninto ambiguity.","operationId":"add_event_type_host_appointments_event_types__event_type_id__hosts_post","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AppointmentHostCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppointmentHost_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/appointments/event-types/{event_type_id}/hosts/{host_user_id}":{"patch":{"tags":["Appointments"],"summary":"Update Event Type Host","description":"Change a host's rotation settings. Omitted fields are left alone.","operationId":"update_event_type_host_appointments_event_types__event_type_id__hosts__host_user_id__patch","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"host_user_id","in":"path","required":true,"schema":{"type":"integer","description":"Host user id.","title":"Host User Id"},"description":"Host user id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AppointmentHostUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppointmentHost_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Appointments"],"summary":"Remove Event Type Host","description":"Remove a host. Existing bookings already assigned to them are NOT\nreassigned - this only changes who future bookings can land on.","operationId":"remove_event_type_host_appointments_event_types__event_type_id__hosts__host_user_id__delete","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"host_user_id","in":"path","required":true,"schema":{"type":"integer","description":"Host user id.","title":"Host User Id"},"description":"Host user id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/appointments/event-types/{event_type_id}/host-groups":{"get":{"tags":["Appointments"],"summary":"List Event Type Host Groups","description":"Groups that partition this event type's hosts for the rotation.","operationId":"list_event_type_host_groups_appointments_event_types__event_type_id__host_groups_get","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_AppointmentHostGroup__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"},"post":{"tags":["Appointments"],"summary":"Create Event Type Host Group","description":"Create a host group. Assign hosts to it via `group_id` on a host.","operationId":"create_event_type_host_group_appointments_event_types__event_type_id__host_groups_post","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AppointmentHostGroupWriteRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppointmentHostGroup_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/appointments/event-types/{event_type_id}/host-groups/{group_id}":{"patch":{"tags":["Appointments"],"summary":"Update Event Type Host Group","description":"Rename a host group.","operationId":"update_event_type_host_group_appointments_event_types__event_type_id__host_groups__group_id__patch","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"Host group id.","title":"Group Id"},"description":"Host group id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AppointmentHostGroupWriteRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppointmentHostGroup_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Appointments"],"summary":"Delete Event Type Host Group","description":"Delete a host group. The hosts in it are NOT removed from the event\ntype - they become ungrouped.","operationId":"delete_event_type_host_group_appointments_event_types__event_type_id__host_groups__group_id__delete","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"group_id","in":"path","required":true,"schema":{"type":"string","description":"Host group id.","title":"Group Id"},"description":"Host group id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/appointments/event-types/{event_type_id}/hosts/{host_user_id}/booking-limits":{"put":{"tags":["Appointments"],"summary":"Set Host Booking Limits","description":"Set one host's OWN booking limit on a team event.\n\nPer kind (`frequency`, `duration`): `inherit` the team default, a `custom` value, or `none`. Admins may set any host's;\na host may set their own, STRICTER than the team default only. Returns the event type with its `limits_meta`.","operationId":"set_host_booking_limits_appointments_event_types__event_type_id__hosts__host_user_id__booking_limits_put","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"host_user_id","in":"path","required":true,"schema":{"type":"integer","description":"Host user id.","title":"Host User Id"},"description":"Host user id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AppointmentHostBookingLimitsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppointmentLimitsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Appointments"],"summary":"Clear Host Booking Limits","description":"Reset one host's own booking limit: every kind inherits the team default again. Same rules as the set.","operationId":"clear_host_booking_limits_appointments_event_types__event_type_id__hosts__host_user_id__booking_limits_delete","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"host_user_id","in":"path","required":true,"schema":{"type":"integer","description":"Host user id.","title":"Host User Id"},"description":"Host user id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppointmentLimitsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/appointments/event-types/{event_type_id}/limits/history":{"get":{"tags":["Appointments"],"summary":"List Booking Limit History","description":"Who changed this event type's booking limits, newest first. Org admins only (403 for anyone else).","operationId":"list_booking_limit_history_appointments_event_types__event_type_id__limits_history_get","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","description":"Event type id.","title":"Event Type Id"},"description":"Event type id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"before_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":1},{"type":"null"}],"description":"Page back: changes older than this history id.","title":"Before Id"},"description":"Page back: changes older than this history id."},{"name":"level","in":"query","required":false,"schema":{"anyOf":[{"enum":["event","host_default","host_override"],"type":"string"},{"type":"null"}],"title":"Level"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_AppointmentLimitHistoryEntry__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/event-types":{"post":{"tags":["Appointments"],"summary":"Create a bookable event type","description":"Create a new event type. Reuses ``EventTypesHandler.handle_create``\nverbatim (slug uniqueness, host wiring, schedule attach), so the result is\nidentical to creating one in the app. ``slug`` must be unique within the org\n(409 on collision); ``length`` is the meeting duration in minutes.","operationId":"create_event_type_appointments_event_types_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateEventTypeRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Create Event Type Appointments Event Types Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/appointments/event-types/{event_type_id}/duplicate":{"post":{"tags":["Appointments"],"summary":"Duplicate an event type (with a '-copy' slug)","description":"Duplicate an event type, generating a unique ``{slug}-copy`` slug and\ncopying its hosts. Mirrors the in-app duplicate path (repo-direct, no\nhandler) using the shared appointments helpers; ``is_admin`` is forced False\nso a host (or the owner) can duplicate, matching ``EventTypePolicy``.","operationId":"duplicate_event_type_appointments_event_types__event_type_id__duplicate_post","parameters":[{"name":"event_type_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Source event-type integer ID.","title":"Event Type Id"},"description":"Source event-type integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Duplicate Event Type Appointments Event Types  Event Type Id  Duplicate Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/appointments/schedules":{"post":{"tags":["Appointments"],"summary":"Create an availability schedule","description":"Create a named availability schedule with weekly rules and optional date overrides.\n\nDefaults to Mon-Fri 09:00-17:00 when ``availability`` is omitted.\nPass ``is_default=True`` to immediately set this as the caller's default\nschedule (persisted via ``update_appointment_settings``).","operationId":"create_schedule_appointments_schedules_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateScheduleRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Create Schedule Appointments Schedules Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"},"get":{"tags":["Appointments"],"summary":"List the caller's availability schedules","description":"List the caller's appointment availability schedules (the \"when am I\nfree?\" working-hours profiles used by event types). This is DISTINCT from\nthe sequencer send-window schedules at ``GET /schedules`` - those drive\nemail send timing, these drive bookability. Each schedule carries its weekly\nrules' owner + a ``is_default`` flag derived from the caller's settings.","operationId":"list_schedules_appointments_schedules_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Schedules Appointments Schedules Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/schedules/{schedule_id}":{"get":{"tags":["Appointments"],"summary":"Get a schedule with availability and linked event types","description":"Return a schedule's full detail: weekly availability rules, date overrides,\nowner info, and the list of event types currently linked to this schedule.\nReturns 404 when the schedule doesn't exist or belongs to another user.","operationId":"get_schedule_appointments_schedules__schedule_id__get","parameters":[{"name":"schedule_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Schedule integer ID.","title":"Schedule Id"},"description":"Schedule integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Get Schedule Appointments Schedules  Schedule Id  Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Appointments"],"summary":"Update a schedule (partial)","description":"Partially update a schedule. Pass only the fields to change.\n\n- ``name`` / ``time_zone``: update schedule metadata.\n- ``availability``: replaces ALL weekly recurring rules (pass every active day).\n- ``overrides``: replaces ALL date-specific overrides.\n- ``is_default``: when True, sets this as the caller's default schedule.","operationId":"update_schedule_appointments_schedules__schedule_id__patch","parameters":[{"name":"schedule_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Schedule integer ID.","title":"Schedule Id"},"description":"Schedule integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateScheduleRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Update Schedule Appointments Schedules  Schedule Id  Patch"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Appointments"],"summary":"Delete a schedule","description":"Delete a schedule. Returns 409 when this is the caller's last schedule\n(mirroring the in-app guard - every user must retain at least one schedule).\nReturns 404 when the schedule does not exist or belongs to another user.","operationId":"delete_schedule_appointments_schedules__schedule_id__delete","parameters":[{"name":"schedule_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Schedule integer ID.","title":"Schedule Id"},"description":"Schedule integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Delete Schedule Appointments Schedules  Schedule Id  Delete"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/appointments/schedules/{schedule_id}/availability":{"get":{"tags":["Appointments"],"summary":"Get availability rules and overrides for a schedule","description":"Return the weekly recurring availability rules and date-specific overrides\nfor the given schedule. Availability entries without a ``date`` are weekly\nrules; entries with a ``date`` are one-time overrides for that calendar day.","operationId":"get_availability_appointments_schedules__schedule_id__availability_get","parameters":[{"name":"schedule_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Schedule integer ID.","title":"Schedule Id"},"description":"Schedule integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Get Availability Appointments Schedules  Schedule Id  Availability Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Appointments"],"summary":"Replace availability rules and/or date overrides for a schedule","description":"Replace weekly availability rules and/or date overrides for a schedule.\n\nBody: ``{\"availability\": [...], \"overrides\": [...]}``\n\n- ``availability``: list of ``{days, start_time, end_time}`` - replaces ALL weekly rules.\n- ``overrides``: list of ``{date, start_time, end_time}`` - replaces ALL date overrides.\n\nOmit a key to leave that set unchanged. At least one key is required.\nMirrors the in-app ``PATCH /schedules/{id}/availability`` logic verbatim.\nTyped via ``UpdateAvailabilityRequest`` so malformed items fail at FastAPI\nvalidation (422) rather than as an opaque 500.","operationId":"update_availability_appointments_schedules__schedule_id__availability_patch","parameters":[{"name":"schedule_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Schedule integer ID.","title":"Schedule Id"},"description":"Schedule integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateAvailabilityRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Update Availability Appointments Schedules  Schedule Id  Availability Patch"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/appointments/schedules/{schedule_id}/set-default":{"post":{"tags":["Appointments"],"summary":"Set a schedule as the caller's default","description":"Mark a schedule as the caller's default availability schedule.\n\nPersists via ``repo.update_appointment_settings(default_schedule_id=...)``\nwhich is identical to the in-app ``PATCH /me`` (profile router) path that\nsets ``default_schedule_id``. The default schedule is used for slot\ngeneration when an event type has no schedule attached (Layer 3 resolution).\nReturns 404 when the schedule does not exist or belongs to another user.","operationId":"set_default_schedule_appointments_schedules__schedule_id__set_default_post","parameters":[{"name":"schedule_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Schedule integer ID.","title":"Schedule Id"},"description":"Schedule integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Set Default Schedule Appointments Schedules  Schedule Id  Set Default Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/appointments/out-of-office":{"post":{"tags":["Appointments"],"summary":"Create an out-of-office entry","description":"Create an out-of-office entry for the calling user. While active, the\nuser's slots are blocked for booking. ``start`` and ``end`` may be local\ncalendar dates paired with ``time_zone`` or legacy ISO-8601 datetimes.\nOptional ``to_user_id`` exposes an alternative teammate booking path.","operationId":"create_ooo_appointments_out_of_office_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateOutOfOfficeRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Create Ooo Appointments Out Of Office Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"},"get":{"tags":["Appointments"],"summary":"List out-of-office entries for the calling user","description":"List all out-of-office entries belonging to the calling user. API keys\nnever receive org-wide admin access, so this always returns only the\ncaller's own entries (equivalent to the non-admin in-app path).","operationId":"list_ooo_appointments_out_of_office_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Ooo Appointments Out Of Office Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/out-of-office/{ooo_uuid}":{"patch":{"tags":["Appointments"],"summary":"Update an out-of-office entry","description":"Update an entry owned by the calling API user.","operationId":"update_ooo_appointments_out_of_office__ooo_uuid__patch","parameters":[{"name":"ooo_uuid","in":"path","required":true,"schema":{"type":"string","description":"UUID of the out-of-office entry to update.","title":"Ooo Uuid"},"description":"UUID of the out-of-office entry to update."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateOutOfOfficeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Update Ooo Appointments Out Of Office  Ooo Uuid  Patch"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Appointments"],"summary":"Delete an out-of-office entry","description":"Delete an out-of-office entry. Only the owner may delete their own\nentry (API keys force ``is_admin=False``). Returns\n``{data: {deleted: true, ooo_uuid}}`` on success.","operationId":"delete_ooo_appointments_out_of_office__ooo_uuid__delete","parameters":[{"name":"ooo_uuid","in":"path","required":true,"schema":{"type":"string","description":"UUID of the out-of-office entry to delete.","title":"Ooo Uuid"},"description":"UUID of the out-of-office entry to delete."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Delete Ooo Appointments Out Of Office  Ooo Uuid  Delete"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/appointments/routing-forms":{"post":{"tags":["Appointments"],"summary":"Create a routing form","description":"Create a new routing form with optional fields and routes.\n\nReturns the created form including its generated slug. ``is_admin`` is\nforced False so the form is owned by the API-key user.","operationId":"create_routing_form_appointments_routing_forms_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateRoutingFormRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Create Routing Form Appointments Routing Forms Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"},"get":{"tags":["Appointments"],"summary":"List routing forms (includes response_count)","description":"List all routing forms owned by the API-key user.\n\n``is_admin`` is forced False - returns only the caller's own forms.\nEach item includes ``response_count`` (total submissions captured).","operationId":"list_routing_forms_appointments_routing_forms_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Routing Forms Appointments Routing Forms Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/routing-forms/{form_id}":{"get":{"tags":["Appointments"],"summary":"Get a single routing form","description":"Return a routing form with its fields, routes, and response_count.\n\nReturns 404 when the form does not exist or belongs to another user.","operationId":"get_routing_form_appointments_routing_forms__form_id__get","parameters":[{"name":"form_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Routing form integer ID.","title":"Form Id"},"description":"Routing form integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Get Routing Form Appointments Routing Forms  Form Id  Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Appointments"],"summary":"Update a routing form (partial)","description":"Partially update a routing form. Only sent fields are changed.\n\nOmit a field to leave it untouched. Slug must be unique in the org (409 on\ncollision). Fields/routes are replaced atomically when present in the body.","operationId":"update_routing_form_appointments_routing_forms__form_id__patch","parameters":[{"name":"form_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Routing form integer ID.","title":"Form Id"},"description":"Routing form integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateRoutingFormRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Update Routing Form Appointments Routing Forms  Form Id  Patch"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Appointments"],"summary":"Delete a routing form (cascades fields and routes)","description":"Delete a routing form permanently. Cascades to its fields and routes.\n\nReturns 404 when the form does not exist or belongs to another user.","operationId":"delete_routing_form_appointments_routing_forms__form_id__delete","parameters":[{"name":"form_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Routing form integer ID.","title":"Form Id"},"description":"Routing form integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Delete Routing Form Appointments Routing Forms  Form Id  Delete"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/appointments/routing-forms/{form_id}/duplicate":{"post":{"tags":["Appointments"],"summary":"Duplicate a routing form (copy with all fields and routes)","description":"Duplicate a routing form. Creates a copy named \"{name} (copy)\" with\na unique slug, copying all fields and routes verbatim.","operationId":"duplicate_routing_form_appointments_routing_forms__form_id__duplicate_post","parameters":[{"name":"form_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Source routing form integer ID.","title":"Form Id"},"description":"Source routing form integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Duplicate Routing Form Appointments Routing Forms  Form Id  Duplicate Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/appointments/routing-forms/{form_id}/responses":{"get":{"tags":["Appointments"],"summary":"List captured responses for a routing form (paginated)","description":"List captured form responses. Paginated via ``skip`` / ``take``.\n\nReturns 404 when the form does not exist or belongs to another user.\nResponse items include: ``id``, ``form_id``, ``responses`` (field answers),\n``routed_to_event_type_id``, and ``created_at``.","operationId":"list_routing_form_responses_appointments_routing_forms__form_id__responses_get","parameters":[{"name":"form_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Routing form integer ID.","title":"Form Id"},"description":"Routing form integer ID."},{"name":"skip","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Number of responses to skip.","default":0,"title":"Skip"},"description":"Number of responses to skip."},{"name":"take","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"description":"Maximum responses to return (max 500).","default":50,"title":"Take"},"description":"Maximum responses to return (max 500)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Routing Form Responses Appointments Routing Forms  Form Id  Responses Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/workflows":{"post":{"tags":["Appointments"],"summary":"Create a workflow","description":"Create a new workflow. Steps define the actions to take; event_type_ids\nattaches the workflow to specific event types (omit or set ``is_active_on_all``\nto apply org-wide). ``trigger`` must be one of: new_booking, before_event,\nafter_event, booking_cancelled, booking_rescheduled. Time-based triggers\n(before_event / after_event) require ``time`` and ``time_unit``.","operationId":"create_workflow_appointments_workflows_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateWorkflowRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Create Workflow Appointments Workflows Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"},"get":{"tags":["Appointments"],"summary":"List all workflows","description":"List all workflows for the organisation.","operationId":"list_workflows_appointments_workflows_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Workflows Appointments Workflows Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/workflows/{workflow_id}":{"get":{"tags":["Appointments"],"summary":"Get a single workflow","description":"Return the full workflow record (steps, linked event types, trigger config).","operationId":"get_workflow_appointments_workflows__workflow_id__get","parameters":[{"name":"workflow_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Workflow integer ID.","title":"Workflow Id"},"description":"Workflow integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Get Workflow Appointments Workflows  Workflow Id  Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Appointments"],"summary":"Update a workflow (partial)","description":"Partially update a workflow. Only the fields you send are changed; omit a\nfield to leave it as-is. Steps are replaced wholesale when provided.","operationId":"update_workflow_appointments_workflows__workflow_id__patch","parameters":[{"name":"workflow_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Workflow integer ID.","title":"Workflow Id"},"description":"Workflow integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateWorkflowRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Update Workflow Appointments Workflows  Workflow Id  Patch"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Appointments"],"summary":"Delete a workflow and cancel pending reminders","description":"Delete a workflow and cancel any pending reminder rows created by it.\nMirrors the in-app router: ``cancel_workflow_reminders`` is called BEFORE\n``delete_workflow`` so reminder FK constraints are satisfied and scheduled\nworker jobs for this workflow never fire after deletion.","operationId":"delete_workflow_appointments_workflows__workflow_id__delete","parameters":[{"name":"workflow_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Workflow integer ID.","title":"Workflow Id"},"description":"Workflow integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/appointments/workflows/{workflow_id}/toggle":{"post":{"tags":["Appointments"],"summary":"Activate or deactivate a workflow","description":"Set the workflow's active state. When deactivating (``active: false``),\nall pending reminders are cancelled first (same behaviour as the in-app\ntoggle) so the reminder worker never fires steps for a disabled workflow.","operationId":"toggle_workflow_appointments_workflows__workflow_id__toggle_post","parameters":[{"name":"workflow_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Workflow integer ID.","title":"Workflow Id"},"description":"Workflow integer ID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ToggleWorkflowRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Toggle Workflow Appointments Workflows  Workflow Id  Toggle Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"}},"/appointments/calendars":{"get":{"tags":["Appointments"],"summary":"List connected calendar accounts","description":"List calendar accounts (Google, Outlook) connected to the caller's\nappointments profile, each with its sub-calendars and selection state.\nReuses the in-app list_calendars logic faithfully.","operationId":"list_calendars_appointments_calendars_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"array","items":{"$ref":"#/components/schemas/ConnectedCalendarResponse"},"title":"Response List Calendars Appointments Calendars Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/calendars/selected":{"post":{"tags":["Appointments"],"summary":"Select a sub-calendar for conflict checking","description":"Add a sub-calendar to the caller's conflict-checking set.\nReuses the in-app select_calendar logic (credential ownership check +\ncreate_selected_calendar). Raises 404 when the credential is not found\nor does not belong to the caller.","operationId":"select_calendar_appointments_calendars_selected_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SelectCalendarRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SelectedCalendarEnvelope"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Appointments"],"summary":"Deselect a sub-calendar from conflict checking","description":"Remove a sub-calendar from the caller's conflict-checking set.\nReuses the in-app deselect_calendar logic (delete_selected_calendar).","operationId":"deselect_calendar_appointments_calendars_selected_delete","parameters":[{"name":"credential_id","in":"query","required":true,"schema":{"type":"integer","title":"Credential Id"}},{"name":"integration","in":"query","required":true,"schema":{"type":"string","title":"Integration"}},{"name":"external_id","in":"query","required":true,"schema":{"type":"string","title":"External Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/appointments/calendars/{credential_id}":{"delete":{"tags":["Appointments"],"summary":"Disconnect a calendar account","description":"Disconnect a calendar account with best-effort token revocation.\nReuses the in-app disconnect_calendar logic (revoke + delete credential +\nclean up destination calendar rows pointing at the removed credential).\nRaises 404 when not found; 403 when it belongs to a different user.","operationId":"disconnect_calendar_appointments_calendars__credential_id__delete","parameters":[{"name":"credential_id","in":"path","required":true,"schema":{"type":"integer","title":"Credential Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/appointments/calendars/destination":{"put":{"tags":["Appointments"],"summary":"Set the destination calendar for new booking events","description":"Set (upsert) the destination calendar where booking events are pushed.\nOptionally scoped to a specific event type via ``event_type_id``. Reuses\nthe in-app set_destination_calendar logic (upsert_destination_calendar).","operationId":"set_destination_calendar_appointments_calendars_destination_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetDestinationCalendarRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DestinationCalendarEnvelope"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"},"get":{"tags":["Appointments"],"summary":"Get the destination calendar (with event-type fallback)","description":"Get the destination calendar for the caller. When ``event_type_id`` is\nprovided, returns the event-type-specific override if one exists, falling\nback to the user-level default. Returns ``{data: null}`` when none is set.\nReuses the in-app get_destination_calendar logic.","operationId":"get_destination_calendar_appointments_calendars_destination_get","parameters":[{"name":"event_type_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Event Type Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DestinationCalendarEnvelope"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/conferencing":{"get":{"tags":["Appointments"],"summary":"List connected conferencing providers","description":"List conferencing providers connected to the caller's appointments profile.\nGoogle Meet is synthesized from any google_calendar credential (it has no\nreal credential row) and is suppressed when google_meet_suppressed is set.\nReuses the in-app list_conferencing logic faithfully.","operationId":"list_conferencing_appointments_conferencing_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"array","items":{"$ref":"#/components/schemas/ConnectedConferencingResponse"},"title":"Response List Conferencing Appointments Conferencing Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/appointments/conferencing/connect/{provider}":{"post":{"tags":["Appointments"],"summary":"Connect a conferencing provider (link-based / no-OAuth only)","description":"Connect a conferencing provider that does not require a browser OAuth\nflow. Supported providers: google_meet, roam, roam_auto, whereby, jitsi.\nZoom and office365_video (Teams) are excluded - they require a browser\nOAuth redirect that cannot be completed via an API key.\n\ngoogle_meet: clears the google_meet_suppressed flag (requires an existing\ngoogle_calendar credential - no credential row is created for Meet itself).\n\nroam, whereby, jitsi: creates a credential row; optional ``link`` is the\nmeeting URL validated against the provider's URL pattern.\n\nroam_auto: creates a stub credential row (no OAuth tokens - the Roam Auto\nintegration requires a prior OAuth flow to be completed in the web app).","operationId":"connect_conferencing_appointments_conferencing_connect__provider__post","parameters":[{"name":"provider","in":"path","required":true,"schema":{"type":"string","description":"Provider: google_meet | roam | roam_auto | whereby | jitsi","title":"Provider"},"description":"Provider: google_meet | roam | roam_auto | whereby | jitsi"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Body_connect_conferencing_appointments_conferencing_connect__provider__post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Connect Conferencing Appointments Conferencing Connect  Provider  Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"}},"/appointments/conferencing/{provider}/disconnect":{"delete":{"tags":["Appointments"],"summary":"Disconnect a conferencing provider","description":"Disconnect a conferencing provider. For real-credential providers\n(zoom, roam, whereby, jitsi, office365_video, roam_auto) this deletes\nthe matching credentials row. Google Meet is special: it is a synthetic\nprovider - disconnect sets google_meet_suppressed and clears the default\nif it pointed at Meet. Reuses the in-app disconnect_conferencing logic.","operationId":"disconnect_conferencing_appointments_conferencing__provider__disconnect_delete","parameters":[{"name":"provider","in":"path","required":true,"schema":{"type":"string","title":"Provider"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/appointments/conferencing/{provider}/link":{"put":{"tags":["Appointments"],"summary":"Set or update a link-based conferencing provider's meeting URL","description":"Set or update the meeting URL for a link-based conferencing provider\n(roam, whereby, jitsi). The provider must already be installed. Validates\nthe URL against the provider's pattern. Reuses the in-app set_provider_link\nlogic (validate + update_credential_key).","operationId":"set_provider_link_appointments_conferencing__provider__link_put","parameters":[{"name":"provider","in":"path","required":true,"schema":{"type":"string","title":"Provider"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Body_set_provider_link_appointments_conferencing__provider__link_put"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Set Provider Link Appointments Conferencing  Provider  Link Put"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"}},"/appointments/conferencing/{provider}/default":{"post":{"tags":["Appointments"],"summary":"Set the default conferencing provider","description":"Set the default conferencing provider for new meetings. For link-based\nproviders (roam, whereby, jitsi) a meeting URL is required (either in the\nrequest or previously stored on the credential). Reuses the in-app\nset_default_conferencing logic.","operationId":"set_default_conferencing_appointments_conferencing__provider__default_post","parameters":[{"name":"provider","in":"path","required":true,"schema":{"type":"string","title":"Provider"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SetDefaultConferencingRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DefaultConferencingEnvelope"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"meetings:run","x-graph8-lifecycle":"active"}},"/appointments/conferencing/default":{"get":{"tags":["Appointments"],"summary":"Get the current default conferencing provider","description":"Get the default conferencing provider. Returns provider, credential_id,\nand link. Returns ``{data: {provider: null}}`` when none is configured.\nReuses the in-app get_default_conferencing logic.","operationId":"get_default_conferencing_appointments_conferencing_default_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DefaultConferencingEnvelope"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/streams":{"get":{"tags":["Snippet"],"summary":"List Org Streams","description":"List the organization's tracking streams (websites) without a repository.\n\nStreams belong to the organization, not to a connected repository, so this\nworks even when the org has connected no repository. Each stream carries its\nwrite key, its domains, `is_default` (the stream `GET /snippet` uses when no\n`stream_id` is given), `repo_id` (the connected repository already using it,\nor null), and a read-only `warning` when it has no allowed domains.","operationId":"list_org_streams_streams_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":1},{"type":"null"}],"description":"Page number (1-indexed). Omit page and limit to get every stream.","title":"Page"},"description":"Page number (1-indexed). Omit page and limit to get every stream."},{"name":"limit","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","maximum":200,"minimum":1},{"type":"null"}],"description":"Streams per page (max 200). Omit page and limit to get every stream.","title":"Limit"},"description":"Streams per page (max 200). Omit page and limit to get every stream."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_StreamInfoResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/snippet":{"get":{"tags":["Snippet"],"summary":"Get Org Snippet","description":"Get the tracking snippet for the authenticated organization.\n\nReturns the write key and pre-built snippets without requiring a\nconnected repository. Pass `stream_id` to choose the stream; otherwise the\norg's main stream is used (its only stream, or the one whose domain matches\nthe org's website). If that is ambiguous the first stream is used as before\nand the response sets `action_required` with `available_streams` to pick from.","operationId":"get_org_snippet_snippet_get","parameters":[{"name":"stream_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Tracking stream to use (from GET /streams). When omitted, the organization's main stream is used: its only stream, or the one matching its website domain.","title":"Stream Id"},"description":"Tracking stream to use (from GET /streams). When omitted, the organization's main stream is used: its only stream, or the one matching its website domain."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SnippetResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/snippet/form":{"get":{"tags":["Snippet"],"summary":"Get Form Template","description":"Generate a ready-to-embed lead-capture HTML form.\n\nReturns a self-contained HTML snippet with:\n- Name + work email + company fields\n- Client-side validation\n- Tracking hook that calls ``window.graph8.track('form_submitted', ...)``\n  so the submission is captured alongside page views and other events\n\nDrop the returned ``html`` into any page that already loads the tracking\nsnippet (see ``GET /snippet``). The form POSTs to your tracking host by\ndefault, but you can override ``action`` to route submissions to your own\nbackend.","operationId":"get_form_template_snippet_form_get","parameters":[{"name":"stream_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Tracking stream whose write key the form uses (from GET /streams). Defaults as in GET /snippet.","title":"Stream Id"},"description":"Tracking stream whose write key the form uses (from GET /streams). Defaults as in GET /snippet."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/data-pipelines/destinations":{"get":{"tags":["Data pipelines"],"summary":"List Destinations","description":"List the organization's data destinations (warehouses, webhooks, ad/CRM targets).\n\nSame list as Data > Connections > Destinations. Secrets (passwords, keys,\nservice-account JSON, tokens) are never returned: each one reads `__SET__`.","operationId":"list_destinations_data_pipelines_destinations_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DataPipelineItems_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/data-pipelines/functions":{"get":{"tags":["Data pipelines"],"summary":"List Functions","description":"List the organization's event functions (transformations run on a sync).\n\nSame list as Data > Connections > Functions. Function environment secrets\nread `__SET__`.","operationId":"list_functions_data_pipelines_functions_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DataPipelineItems_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/data-pipelines/syncs":{"get":{"tags":["Data pipelines"],"summary":"List Syncs","description":"List the organization's syncs: each one connects a stream or connector to a destination.\n\nSame list as Data > Connections > Syncs. Each item carries `fromId`\n(stream or connector id), `toId` (destination id) and its settings. Per-sync\nfunction secrets read `__SET__`. Run history: GET /data-pipelines/syncs/{sync_id}/tasks.","operationId":"list_syncs_data_pipelines_syncs_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DataPipelineItems_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/data-pipelines/syncs/{sync_id}/tasks":{"get":{"tags":["Data pipelines"],"summary":"List Sync Tasks","description":"A sync's run history: when each run started, its status and any error.\n\nConnector (service) syncs only; a stream-to-destination sync streams events\ncontinuously and has no runs. 404 when the sync is not in this organization.","operationId":"list_sync_tasks_data_pipelines_syncs__sync_id__tasks_get","parameters":[{"name":"sync_id","in":"path","required":true,"schema":{"type":"string","pattern":"^[A-Za-z0-9][A-Za-z0-9._:-]{0,255}$","description":"Sync id (from GET /data-pipelines/syncs).","title":"Sync Id"},"description":"Sync id (from GET /data-pipelines/syncs)."},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":40},{"type":"null"}],"description":"Only runs in this status (e.g. SUCCESS, FAILED, RUNNING).","title":"Status"},"description":"Only runs in this status (e.g. SUCCESS, FAILED, RUNNING)."},{"name":"started_after","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":40},{"type":"null"}],"description":"Only runs started at or after (ISO 8601).","title":"Started After"},"description":"Only runs started at or after (ISO 8601)."},{"name":"started_before","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":40},{"type":"null"}],"description":"Only runs started before (ISO 8601).","title":"Started Before"},"description":"Only runs started before (ISO 8601)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DataPipelineItems_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/data-pipelines/streams/{stream_id}/events":{"get":{"tags":["Data pipelines"],"summary":"List Stream Events","description":"Live events: the latest events a tracking stream received, newest first.\n\nSame feed as Data > Connections > Live events. Use it to check a snippet\ninstall (are page views arriving from the right site?) or to see rejected\nevents (`levels=error`). The sender's IP address and HTTP headers are\ndropped from every entry. 404 when the stream is not in this organization.","operationId":"list_stream_events_data_pipelines_streams__stream_id__events_get","parameters":[{"name":"stream_id","in":"path","required":true,"schema":{"type":"string","pattern":"^[A-Za-z0-9][A-Za-z0-9._:-]{0,255}$","description":"Stream id (from GET /streams).","title":"Stream Id"},"description":"Stream id (from GET /streams)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Newest events to return, 1-200.","default":50,"title":"Limit"},"description":"Newest events to return, 1-200."},{"name":"start","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":40},{"type":"null"}],"description":"Only events at or after (ISO 8601).","title":"Start"},"description":"Only events at or after (ISO 8601)."},{"name":"end","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":40},{"type":"null"}],"description":"Only events before (ISO 8601).","title":"End"},"description":"Only events before (ISO 8601)."},{"name":"levels","in":"query","required":false,"schema":{"anyOf":[{"enum":["error","warn","info","debug"],"type":"string"},{"type":"null"}],"description":"Only entries at this log level (e.g. error = rejected events).","title":"Levels"},"description":"Only entries at this log level (e.g. error = rejected events)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DataPipelineItems_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/inbox/meetings/{meeting_id}/transcript-link":{"post":{"tags":["AI Inbox"],"summary":"Link Meeting Transcript","description":"Attach an existing transcript to a meeting.\n\nContacts nobody. It corrects the RECORD - which recording belongs to which\ncalendar event - when the automatic match got it wrong or never ran.\n\nWho may then read that transcript is a separate question, answered by\n`PATCH /inbox/meetings/{id}/sensitivity`.","operationId":"link_meeting_transcript_inbox_meetings__meeting_id__transcript_link_post","parameters":[{"name":"meeting_id","in":"path","required":true,"schema":{"type":"string","description":"Meeting id, as returned by `GET /inbox/meetings`.","title":"Meeting Id"},"description":"Meeting id, as returned by `GET /inbox/meetings`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MeetingTranscriptLinkRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"},"delete":{"tags":["AI Inbox"],"summary":"Clear Meeting Transcript Link","description":"Detach the transcript from a meeting.\n\nBreaks the LINK, not the transcript: the recording and its text survive\nand can be attached to the right meeting instead.","operationId":"clear_meeting_transcript_link_inbox_meetings__meeting_id__transcript_link_delete","parameters":[{"name":"meeting_id","in":"path","required":true,"schema":{"type":"string","description":"Meeting id, as returned by `GET /inbox/meetings`.","title":"Meeting Id"},"description":"Meeting id, as returned by `GET /inbox/meetings`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/inbox/meetings/{meeting_id}/no-transcript":{"post":{"tags":["AI Inbox"],"summary":"Mark Meeting No Transcript Expected","description":"Say that this meeting was never recorded, so stop waiting for one.\n\nDistinguishes \"nothing was captured\" from \"the recording has not arrived\nyet\", which is what stops the meeting sitting in a pending state forever.","operationId":"mark_meeting_no_transcript_expected_inbox_meetings__meeting_id__no_transcript_post","parameters":[{"name":"meeting_id","in":"path","required":true,"schema":{"type":"string","description":"Meeting id, as returned by `GET /inbox/meetings`.","title":"Meeting Id"},"description":"Meeting id, as returned by `GET /inbox/meetings`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/inbox/meetings/{meeting_id}/sensitivity":{"patch":{"tags":["AI Inbox"],"summary":"Set Meeting Sensitivity","description":"CHANGE WHO MAY READ THE RECORDING OF THIS MEETING.\n\n`private` HIDES the transcript from everyone except the meeting's\nparticipants. `normal` EXPOSES it to the organisation again - and a\ntranscript that has been read cannot be un-read, so going back to `normal`\nis not a reversible edit in any sense that matters.\n\nOnly a PARTICIPANT may change it; anyone else gets a 403. Classified\n`destructive`, so it needs `inbox:delete` rather than riding along with\n`inbox:write` - a key that triages the inbox should not also be able to\npublish a private recording.\n\n`sensitivity` is REQUIRED here. The app defaults a missing key to\n`normal`, which is the exposing direction, so this contract refuses to\nguess.","operationId":"set_meeting_sensitivity_inbox_meetings__meeting_id__sensitivity_patch","parameters":[{"name":"meeting_id","in":"path","required":true,"schema":{"type":"string","description":"Meeting id, as returned by `GET /inbox/meetings`.","title":"Meeting Id"},"description":"Meeting id, as returned by `GET /inbox/meetings`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MeetingSensitivityRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/inbox/meetings/my-tasks":{"get":{"tags":["AI Inbox"],"summary":"List My Meeting Tasks","description":"Every meeting follow-up assigned to the caller, across all meetings.\n\nDeclared BEFORE nothing in this router, but registered BEFORE\n`meetings_router`: `GET /inbox/meetings/{meeting_id}` already ships, and\nthe parameter route would otherwise match `my-tasks` and look it up as a\nmeeting id.\n\nStrictly meeting-derived tasks, not a general task list - see\n`GET /tasks` for that. Returns an empty list, not an error, when the\ncaller has no team-member row in this organisation, which is what an\norg-scoped key will see.","operationId":"list_my_meeting_tasks_inbox_meetings_my_tasks_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxOpsListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/inbox/meetings/{meeting_id}/assignable-users":{"get":{"tags":["AI Inbox"],"summary":"List Assignable Meeting Users","description":"Who a task on this meeting may be given to.\n\nPARTICIPANTS ONLY, mapped to their team-member records. Read this before\ncreating a task: the server re-validates the assignee against the same\nlist, so an arbitrary colleague is refused rather than silently accepted.","operationId":"list_assignable_meeting_users_inbox_meetings__meeting_id__assignable_users_get","parameters":[{"name":"meeting_id","in":"path","required":true,"schema":{"type":"string","description":"Meeting id, as returned by `GET /inbox/meetings`.","title":"Meeting Id"},"description":"Meeting id, as returned by `GET /inbox/meetings`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxOpsListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/inbox/meetings/{meeting_id}/tasks":{"get":{"tags":["AI Inbox"],"summary":"List Meeting Tasks","description":"Follow-ups hung off this meeting, filtered by the caller's task\nvisibility - team-only tasks do not cross team boundaries just because the\ncaller can open the meeting.","operationId":"list_meeting_tasks_inbox_meetings__meeting_id__tasks_get","parameters":[{"name":"meeting_id","in":"path","required":true,"schema":{"type":"string","description":"Meeting id, as returned by `GET /inbox/meetings`.","title":"Meeting Id"},"description":"Meeting id, as returned by `GET /inbox/meetings`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxOpsListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"},"post":{"tags":["AI Inbox"],"summary":"Create Meeting Task","description":"Create a follow-up on this meeting.\n\nThe meeting and its transcript are filled in from the meeting itself, so\nthe task stays traceable to what was said. The assignee must be a\nPARTICIPANT - checked server-side, because a client-side filter is not a\npermission.","operationId":"create_meeting_task_inbox_meetings__meeting_id__tasks_post","parameters":[{"name":"meeting_id","in":"path","required":true,"schema":{"type":"string","description":"Meeting id, as returned by `GET /inbox/meetings`.","title":"Meeting Id"},"description":"Meeting id, as returned by `GET /inbox/meetings`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MeetingTaskCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/inbox/meetings/tasks/{task_id}":{"patch":{"tags":["AI Inbox"],"summary":"Update Meeting Task","description":"Patch a meeting task. Reassignment re-checks participant scope.\n\nTHREE-STATE nullable fields: omit `assignee_user_id` or\n`due_date` to leave it alone, send it as `null` to CLEAR it. The proxy\nforwards with `exclude_unset=True` precisely so the app can still tell\nthose apart - dumping every field would turn each PATCH into a full\noverwrite that cleared whatever the caller did not mention.\n\nPass `expected_updated_at` to refuse the write if someone else moved the\ntask since you read it.","operationId":"update_meeting_task_inbox_meetings_tasks__task_id__patch","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Meeting task id.","title":"Task Id"},"description":"Meeting task id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MeetingTaskUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"},"delete":{"tags":["AI Inbox"],"summary":"Delete Meeting Task","description":"Delete a meeting follow-up. The meeting and its transcript survive.","operationId":"delete_meeting_task_inbox_meetings_tasks__task_id__delete","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Meeting task id.","title":"Task Id"},"description":"Meeting task id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"meetings:delete","x-graph8-lifecycle":"active"}},"/inbox/meetings":{"get":{"tags":["Meetings"],"summary":"List Meetings","description":"List meetings as compact summary cards.\n\nThe default visibility scope follows the caller's RBAC. Pass\n`participant_email` to scope down to a specific contact's meetings\n(matched across organizer + owner + attendees). Transcript content\nis returned only as a short summary preview; call the detail\nendpoint for full transcript text.","operationId":"list_meetings_inbox_meetings_get","parameters":[{"name":"participant_email","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"string"}},{"type":"null"}],"description":"Filter to meetings where ANY of the provided emails appears as organizer, owner, or attendee (case-insensitive, OR-matched). Repeat the param for multiple emails.","title":"Participant Email"},"description":"Filter to meetings where ANY of the provided emails appears as organizer, owner, or attendee (case-insensitive, OR-matched). Repeat the param for multiple emails."},{"name":"scope","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Visibility scope: 'my' (your meetings) or 'all' (org-wide, requires meetings:see_all)","title":"Scope"},"description":"Visibility scope: 'my' (your meetings) or 'all' (org-wide, requires meetings:see_all)"},{"name":"timeframe","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"'all', 'upcoming', or 'past' (default: past)","title":"Timeframe"},"description":"'all', 'upcoming', or 'past' (default: past)"},{"name":"has_transcript","in":"query","required":false,"schema":{"anyOf":[{"type":"boolean"},{"type":"null"}],"description":"True = transcript linked; False = no transcript","title":"Has Transcript"},"description":"True = transcript linked; False = no transcript"},{"name":"internal_mode","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Internal meeting visibility. 'include_internal' returns ALL meetings (team syncs, internal-only attendees). 'exclude_internal' drops any meeting with no external attendees. Omitting respects the org policy default (most orgs default to exclude_internal). Pass include_internal to see team/standup meetings the default would hide.","title":"Internal Mode"},"description":"Internal meeting visibility. 'include_internal' returns ALL meetings (team syncs, internal-only attendees). 'exclude_internal' drops any meeting with no external attendees. Omitting respects the org policy default (most orgs default to exclude_internal). Pass include_internal to see team/standup meetings the default would hide."},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Match title or transcript text","title":"Search"},"description":"Match title or transcript text"},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number","default":1,"title":"Page"},"description":"Page number"},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Items per page","default":50,"title":"Page Size"},"description":"Items per page"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_MeetingSummary__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/inbox/meetings/booked":{"get":{"tags":["Meetings"],"summary":"Meetings Booked","description":"Count + recent list of booked meetings (not cancelled, not deleted,\nnot private-sensitivity).\n\nOrg-scoped to the authenticated key's organization. Returns metadata\nonly (title / time / status / attendee count) — never transcript\ncontent. Finer per-user / `meetings:see_all` scoping is tracked as a\nfollow-up. Registered before `/{meeting_id}` so 'booked' isn't captured\nas an id.","operationId":"meetings_booked_inbox_meetings_booked_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Lookback window in days","default":30,"title":"Days"},"description":"Lookback window in days"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"description":"Max meetings per page","default":20,"title":"Limit"},"description":"Max meetings per page"},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"1-based page over the booked list","default":1,"title":"Page"},"description":"1-based page over the booked list"},{"name":"upcoming_only","in":"query","required":false,"schema":{"type":"boolean","description":"Only meetings from now forward","default":false,"title":"Upcoming Only"},"description":"Only meetings from now forward"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MeetingsBookedResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/inbox/meetings/{meeting_id}":{"get":{"tags":["Meetings"],"summary":"Get Meeting","description":"Get a single meeting by ID with full transcript bundled inline.\n\nTranscript content is included when the caller is a participant or\nhas the `meetings:see_transcripts` permission. Otherwise the response\nsets `transcript_redacted=true` and omits the transcript body\n(status / IDs remain visible).","operationId":"get_meeting_inbox_meetings__meeting_id__get","parameters":[{"name":"meeting_id","in":"path","required":true,"schema":{"type":"string","description":"Meeting ID (CalendarEvent.id)","title":"Meeting Id"},"description":"Meeting ID (CalendarEvent.id)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MeetingDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"}},"/inbox/channels/{channel_id}/comments":{"get":{"tags":["AI Inbox"],"summary":"List Channel Comments","description":"Internal notes on a conversation. The customer never sees these.","operationId":"list_channel_comments_inbox_channels__channel_id__comments_get","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Conversation id.","title":"Channel Id"},"description":"Conversation id."},{"name":"channel_type","in":"query","required":true,"schema":{"enum":["email","chat","phone","sms","heyreach","meetings","support","all"],"type":"string","description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels, so this is what identifies the conversation, not a filter.","title":"Channel Type"},"description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels, so this is what identifies the conversation, not a filter."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"},"post":{"tags":["AI Inbox"],"summary":"Add Channel Comment","description":"Leave an INTERNAL note. Not a reply - the customer never sees it.\n\nMENTIONING SOMEONE CREATES THEM A TASK in the Work app. The two mention\nlists are additive rather than alternatives: an id with no matching email\nstill gets the task, it just gets no notification, so send both to get the\nbell as well.\n\nAttachments must already be uploaded; only their token and key are\nload-bearing, because the server re-validates and never trusts a\nclient-sent name, size or type.","operationId":"add_channel_comment_inbox_channels__channel_id__comments_post","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Conversation id.","title":"Channel Id"},"description":"Conversation id."},{"name":"channel_type","in":"query","required":true,"schema":{"enum":["email","chat","phone","sms","heyreach","meetings","support","all"],"type":"string","description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels, so this is what identifies the conversation, not a filter.","title":"Channel Type"},"description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels, so this is what identifies the conversation, not a filter."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CommentCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/channels/{channel_id}/assignee-eligibility":{"get":{"tags":["AI Inbox"],"summary":"Get Assignee Eligibility","description":"Who can be given this conversation, and who cannot.\n\nRead this before assigning: eligibility depends on the channel and on\nmailbox access, so a user who appears in `/inbox/users` is not necessarily\nassignable to THIS thread.","operationId":"get_assignee_eligibility_inbox_channels__channel_id__assignee_eligibility_get","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Conversation id.","title":"Channel Id"},"description":"Conversation id."},{"name":"channel_type","in":"query","required":true,"schema":{"enum":["email","chat","phone","sms","heyreach","meetings","support","all"],"type":"string","description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels, so this is what identifies the conversation, not a filter.","title":"Channel Type"},"description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels, so this is what identifies the conversation, not a filter."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/channels/{channel_id}/assign":{"post":{"tags":["AI Inbox"],"summary":"Assign Channel","description":"Give a conversation to one or more people.\n\nOwnership is SHARED, not singular: assigning ADDS people rather than\nreplacing whoever is already there. Take someone off with\n`DELETE /inbox/channels/{id}/assign`.","operationId":"assign_channel_inbox_channels__channel_id__assign_post","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Conversation id.","title":"Channel Id"},"description":"Conversation id."},{"name":"channel_type","in":"query","required":true,"schema":{"enum":["email","chat","phone","sms","heyreach","meetings","support","all"],"type":"string","description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels, so this is what identifies the conversation, not a filter.","title":"Channel Type"},"description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels, so this is what identifies the conversation, not a filter."},{"name":"linkedin_account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"LinkedIn account id. Required only for `heyreach`, where the id is account-scoped and ambiguous without it.","title":"Linkedin Account Id"},"description":"LinkedIn account id. Required only for `heyreach`, where the id is account-scoped and ambiguous without it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssignmentCreateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"},"delete":{"tags":["AI Inbox"],"summary":"Unassign Channel","description":"Take ONE person off a conversation. The others keep it.","operationId":"unassign_channel_inbox_channels__channel_id__assign_delete","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Conversation id.","title":"Channel Id"},"description":"Conversation id."},{"name":"assignee_email","in":"query","required":true,"schema":{"type":"string","description":"The person to take off.","title":"Assignee Email"},"description":"The person to take off."},{"name":"channel_type","in":"query","required":true,"schema":{"enum":["email","chat","phone","sms","heyreach","meetings","support","all"],"type":"string","description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels, so this is what identifies the conversation, not a filter.","title":"Channel Type"},"description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels, so this is what identifies the conversation, not a filter."},{"name":"linkedin_account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"LinkedIn account id. Required only for `heyreach`, where the id is account-scoped and ambiguous without it.","title":"Linkedin Account Id"},"description":"LinkedIn account id. Required only for `heyreach`, where the id is account-scoped and ambiguous without it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/inbox/users":{"get":{"tags":["AI Inbox"],"summary":"List Inbox Users","description":"Everyone in the organisation, as the inbox sees them.\n\nThe directory an assignment draws from - but eligibility for a SPECIFIC\nconversation is a separate question, answered by\n`/inbox/channels/{id}/assignee-eligibility`.","operationId":"list_inbox_users_inbox_users_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/channels/{channel_id}/ai-pause":{"post":{"tags":["AI Inbox"],"summary":"Set Channel Ai Pause","description":"Stop the AI answering THIS conversation, or let it resume.\n\nScoped to the one thread: pausing here does not disable the responder\nanywhere else. This is the handover switch - pause it when a human takes\nover, so the customer does not get two replies.\n\n`paused` is explicit rather than a toggle, so a retried request is\nidempotent instead of flipping the state back.","operationId":"set_channel_ai_pause_inbox_channels__channel_id__ai_pause_post","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Conversation id.","title":"Channel Id"},"description":"Conversation id."},{"name":"channel_type","in":"query","required":true,"schema":{"enum":["email","chat","phone","sms","heyreach","meetings","support","all"],"type":"string","description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels, so this is what identifies the conversation, not a filter.","title":"Channel Type"},"description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels, so this is what identifies the conversation, not a filter."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AiPauseRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/channels/{channel_id}/tags":{"post":{"tags":["AI Inbox"],"summary":"Add Channel Tag","description":"Attach an existing tag to a conversation.\n\nThe tag must already exist - this links, it does not create.","operationId":"add_channel_tag_inbox_channels__channel_id__tags_post","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Conversation id.","title":"Channel Id"},"description":"Conversation id."},{"name":"channel_type","in":"query","required":true,"schema":{"enum":["email","chat","phone","sms","heyreach","meetings","support","all"],"type":"string","description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels, so this is what identifies the conversation, not a filter.","title":"Channel Type"},"description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels, so this is what identifies the conversation, not a filter."},{"name":"linkedin_account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"LinkedIn account id. Required only for `heyreach`, where the id is account-scoped and ambiguous without it.","title":"Linkedin Account Id"},"description":"LinkedIn account id. Required only for `heyreach`, where the id is account-scoped and ambiguous without it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/developer_api__interfaces__dtos__inbox_collab__TagRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"},"delete":{"tags":["AI Inbox"],"summary":"Remove Channel Tag","description":"Take a tag off a conversation. The tag itself survives.","operationId":"remove_channel_tag_inbox_channels__channel_id__tags_delete","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Conversation id.","title":"Channel Id"},"description":"Conversation id."},{"name":"tag_id","in":"query","required":true,"schema":{"type":"string","description":"The tag to remove.","title":"Tag Id"},"description":"The tag to remove."},{"name":"channel_type","in":"query","required":true,"schema":{"enum":["email","chat","phone","sms","heyreach","meetings","support","all"],"type":"string","description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels, so this is what identifies the conversation, not a filter.","title":"Channel Type"},"description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels, so this is what identifies the conversation, not a filter."},{"name":"linkedin_account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"LinkedIn account id. Required only for `heyreach`, where the id is account-scoped and ambiguous without it.","title":"Linkedin Account Id"},"description":"LinkedIn account id. Required only for `heyreach`, where the id is account-scoped and ambiguous without it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/inbox/workspaces":{"get":{"tags":["AI Inbox"],"summary":"List Inbox Workspaces","description":"Inbox workspaces - the mailbox groupings a team works out of.\n\nPLURAL here, though the app splits reads onto `/workspace` and the one\nwrite onto `/workspaces`. Two paths one letter apart do not belong in a\npublic contract.","operationId":"list_inbox_workspaces_inbox_workspaces_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":20,"title":"Page Size"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/workspaces/unread-counts":{"get":{"tags":["AI Inbox"],"summary":"Get Workspace Unread Counts","description":"Unread per workspace, in one call.\n\nDeclared BEFORE `/workspaces/{workspace_id}` so the literal wins - the id\nroute would otherwise match `unread-counts` and fail parsing it as a UUID.","operationId":"get_workspace_unread_counts_inbox_workspaces_unread_counts_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/workspaces/sequence-channels/{sequence_id}":{"get":{"tags":["AI Inbox"],"summary":"Get Sequence Channels","description":"The conversations a sequence produced.\n\nThe bridge between a sequence and its replies: what went out, and what\ncame back.","operationId":"get_sequence_channels_inbox_workspaces_sequence_channels__sequence_id__get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/workspaces/{workspace_id}":{"get":{"tags":["AI Inbox"],"summary":"Get Inbox Workspace","description":"One workspace, with its mailboxes.","operationId":"get_inbox_workspace_inbox_workspaces__workspace_id__get","parameters":[{"name":"workspace_id","in":"path","required":true,"schema":{"type":"string","description":"Workspace id (UUID).","title":"Workspace Id"},"description":"Workspace id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/workspaces/{workspace_id}/mailboxes":{"post":{"tags":["AI Inbox"],"summary":"Add Mailbox To Workspace","description":"Put a mailbox into a workspace.\n\nIDEMPOTENT: adding a mailbox that is already a member is a no-op, and the\nresponse says which happened rather than failing.\n\nThis one handler wants a `PropelAuthUser` rather than the shared principal,\nso it gets one from `build_api_principal` - resolved from the validated\nkey, never client-supplied.","operationId":"add_mailbox_to_workspace_inbox_workspaces__workspace_id__mailboxes_post","parameters":[{"name":"workspace_id","in":"path","required":true,"schema":{"type":"string","description":"Workspace id (UUID).","title":"Workspace Id"},"description":"Workspace id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Body_add_mailbox_to_workspace_inbox_workspaces__workspace_id__mailboxes_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/mailboxes":{"get":{"tags":["AI Inbox"],"summary":"List Inbox Mailboxes","description":"Mailboxes with their AI Inbox sync state.\n\nEach row carries the mailbox record PLUS `cron_status`, `auto_respond`,\n`is_supported`, `has_credential_error` and `last_unread_limit` - the\ninbox-only columns `/mailboxes` does not have.","operationId":"list_inbox_mailboxes_inbox_mailboxes_get","parameters":[{"name":"user_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Whose PERSONAL mailboxes to include. Defaults to the human who minted this key. An org-scoped key has no human, so it sees the team mailboxes only.","title":"User Email"},"description":"Whose PERSONAL mailboxes to include. Defaults to the human who minted this key. An org-scoped key has no human, so it sees the team mailboxes only."},{"name":"provider","in":"query","required":false,"schema":{"anyOf":[{"enum":["google_mailbox","smtp"],"type":"string"},{"type":"null"}],"description":"Filter by connection type.","title":"Provider"},"description":"Filter by connection type."},{"name":"category","in":"query","required":false,"schema":{"anyOf":[{"enum":["team","personal"],"type":"string"},{"type":"null"}],"description":"`team` (shared) or `personal` (owner-only).","title":"Category"},"description":"`team` (shared) or `personal` (owner-only)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxOpsListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/mailboxes/all":{"get":{"tags":["AI Inbox"],"summary":"List All Inbox Mailboxes","description":"Team AND personal mailboxes in one list, unfiltered.\n\nA three-segment LITERAL, declared before nothing that would swallow it -\nthere is no `/inbox/mailboxes/{mailbox}` route, only deeper ones - but\nkept distinct from `GET /inbox/mailboxes` because that route defaults to\na narrower set and callers reading only the obvious one would miss\nmailboxes.","operationId":"list_all_inbox_mailboxes_inbox_mailboxes_all_get","parameters":[{"name":"user_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Whose personal mailboxes to include. Defaults to this key's human.","title":"User Email"},"description":"Whose personal mailboxes to include. Defaults to this key's human."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxOpsListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/mailboxes/paginated":{"get":{"tags":["AI Inbox"],"summary":"List Inbox Mailboxes Paginated","description":"Mailboxes with their sync state, paged and filterable - the settings\nscreen's list.\n\nEvery VISIBLE mailbox is returned, disconnected ones included, and each is\nannotated with `can_send` / `send_blocked_reason` for THIS caller, so a\nmailbox the key may see but not send from is distinguishable before a send\nis attempted. `total_count` carries the unpaged total. Credentials are\nscrubbed from every row.","operationId":"list_inbox_mailboxes_paginated_inbox_mailboxes_paginated_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":20,"title":"Page Size"}},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"enum":["RUNNING","STOPPED"],"type":"string"},{"type":"null"}],"description":"`RUNNING` (being polled) or `STOPPED`.","title":"Status"},"description":"`RUNNING` (being polled) or `STOPPED`."},{"name":"provider","in":"query","required":false,"schema":{"anyOf":[{"enum":["google_mailbox","smtp"],"type":"string"},{"type":"null"}],"description":"Filter by connection type.","title":"Provider"},"description":"Filter by connection type."},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Substring of the mailbox address.","title":"Search"},"description":"Substring of the mailbox address."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxOpsListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/mailboxes/associated-sequences":{"post":{"tags":["AI Inbox"],"summary":"List Mailbox Associated Sequences","description":"Which sequences have threads in these mailboxes.\n\nA POST because the mailbox list is a body; it reads and writes nothing,\nso it gates on `inbox:read`.\n\nKeyed by mailbox ADDRESS. `/mailboxes/{mailbox_id}/associated-sequences`\nis the same question asked of one mailbox by its numeric id - a different\nkey, which is why this is not folded into it.","operationId":"list_mailbox_associated_sequences_inbox_mailboxes_associated_sequences_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MailboxAddressesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxOpsListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/mailboxes/{mailbox}/sync":{"get":{"tags":["AI Inbox"],"summary":"Get Inbox Mailbox Sync","description":"Is this mailbox being polled, and how did the last round go.\n\nA mailbox that was never connected is not an error - it answers\n`{\"status\": \"STOPPED\"}`.\n\nNOTE the asymmetry this proxy has to respect: the internal handler takes\nNO `current_user`, while its siblings do. Supplying one would be a\nTypeError on every call.","operationId":"get_inbox_mailbox_sync_inbox_mailboxes__mailbox__sync_get","parameters":[{"name":"mailbox","in":"path","required":true,"schema":{"type":"string","description":"The mailbox ADDRESS, e.g. `sales@acme.com`. Not a numeric id.","title":"Mailbox"},"description":"The mailbox ADDRESS, e.g. `sales@acme.com`. Not a numeric id."},{"name":"provider","in":"query","required":true,"schema":{"enum":["google_mailbox","smtp"],"type":"string","description":"How the mailbox is connected. REQUIRED and not inferred: the same address can be connected either way, and guessing would act on the wrong transport. Closed to a Literal so an unknown value is a 422 naming both, rather than a `ValueError` raised inside the handler.","title":"Provider"},"description":"How the mailbox is connected. REQUIRED and not inferred: the same address can be connected either way, and guessing would act on the wrong transport. Closed to a Literal so an unknown value is a 422 naming both, rather than a `ValueError` raised inside the handler."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"},"post":{"tags":["AI Inbox"],"summary":"Start Inbox Mailbox Sync","description":"START POLLING this mailbox.\n\nREACHES OUTSIDE GRAPH8: from here on the platform connects to the\ncustomer's Google or IMAP server with their stored credentials, on a\nschedule, until it is stopped. Classified `external`, so it needs\n`inbox:run` rather than plain write.\n\nIt contacts no recipient - nothing is SENT by turning sync on. What it\ncan lead to is the AI answering on this mailbox, which is governed\nseparately by `auto_respond`.\n\nRefuses with 400 if the mailbox is already running, so a retry is safe\nrather than doubling the polling.\n\n202 because the first sync round happens on the org-level worker's next\npass, not inside this request.","operationId":"start_inbox_mailbox_sync_inbox_mailboxes__mailbox__sync_post","parameters":[{"name":"mailbox","in":"path","required":true,"schema":{"type":"string","description":"The mailbox ADDRESS, e.g. `sales@acme.com`. Not a numeric id.","title":"Mailbox"},"description":"The mailbox ADDRESS, e.g. `sales@acme.com`. Not a numeric id."},{"name":"provider","in":"query","required":true,"schema":{"enum":["google_mailbox","smtp"],"type":"string","description":"How the mailbox is connected. REQUIRED and not inferred: the same address can be connected either way, and guessing would act on the wrong transport. Closed to a Literal so an unknown value is a 422 naming both, rather than a `ValueError` raised inside the handler.","title":"Provider"},"description":"How the mailbox is connected. REQUIRED and not inferred: the same address can be connected either way, and guessing would act on the wrong transport. Closed to a Literal so an unknown value is a 422 naming both, rather than a `ValueError` raised inside the handler."},{"name":"display_name","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Label shown beside the address.","title":"Display Name"},"description":"Label shown beside the address."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"},"delete":{"tags":["AI Inbox"],"summary":"Stop Inbox Mailbox Sync","description":"STOP polling this mailbox.\n\nStops the sync, not the mailbox: the threads already pulled in stay, and\nthe mailbox record itself is untouched. 404 if this mailbox was never\nconnected to the inbox.","operationId":"stop_inbox_mailbox_sync_inbox_mailboxes__mailbox__sync_delete","parameters":[{"name":"mailbox","in":"path","required":true,"schema":{"type":"string","description":"The mailbox ADDRESS, e.g. `sales@acme.com`. Not a numeric id.","title":"Mailbox"},"description":"The mailbox ADDRESS, e.g. `sales@acme.com`. Not a numeric id."},{"name":"provider","in":"query","required":true,"schema":{"enum":["google_mailbox","smtp"],"type":"string","description":"How the mailbox is connected. REQUIRED and not inferred: the same address can be connected either way, and guessing would act on the wrong transport. Closed to a Literal so an unknown value is a 422 naming both, rather than a `ValueError` raised inside the handler.","title":"Provider"},"description":"How the mailbox is connected. REQUIRED and not inferred: the same address can be connected either way, and guessing would act on the wrong transport. Closed to a Literal so an unknown value is a 422 naming both, rather than a `ValueError` raised inside the handler."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/inbox/mailboxes/activate":{"post":{"tags":["AI Inbox"],"summary":"Activate Inbox Mailboxes","description":"Start polling SEVERAL mailboxes, each with its own provider.\n\nNOT ATOMIC, and the failure shape is the thing to know: the app returns\n400 if ANY mailbox fails, but the ones that succeeded REMAIN ACTIVATED.\nThe 400 body carries `successful` and `failed`, so read them rather than\nassuming the call did nothing.\n\nReaches outside graph8 for the same reason the single-mailbox start does.","operationId":"activate_inbox_mailboxes_inbox_mailboxes_activate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MailboxActivateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"}},"/inbox/mailboxes/deactivate":{"post":{"tags":["AI Inbox"],"summary":"Deactivate Inbox Mailboxes","description":"Stop polling several mailboxes at once.\n\nTakes the same body as activate - the campaign and auto-respond fields are\nsimply ignored on this path, which is the app's own shape and is left\nalone rather than split into a narrower model that would drift from it.","operationId":"deactivate_inbox_mailboxes_inbox_mailboxes_deactivate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MailboxActivateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/mailboxes/bulk":{"patch":{"tags":["AI Inbox"],"summary":"Toggle Inbox Mailboxes","description":"Flip several mailboxes on or off by address, and optionally set\nauto-respond on all of them in the same call.\n\nPARTIALLY TOLERANT where activate is not: this one reports failures in the\nbody and still returns 200. Check `total_failed`.\n\n`activate` is explicit rather than a toggle, so a retried request is\nidempotent instead of putting the mailboxes back the way they were.","operationId":"toggle_inbox_mailboxes_inbox_mailboxes_bulk_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MailboxToggleRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"}},"/inbox/mailboxes/{mailbox}/revalidate":{"post":{"tags":["AI Inbox"],"summary":"Revalidate Inbox Mailbox","description":"Re-check this mailbox's credentials and folders, and store the answer.\n\nContacts no recipient. It connects to the provider to find out whether the\nstored credentials still work, then writes `is_supported`, the error\nmessage and the credential-error flag back onto the sync record - which is\nwhat makes a mailbox that silently stopped working visible.","operationId":"revalidate_inbox_mailbox_inbox_mailboxes__mailbox__revalidate_post","parameters":[{"name":"mailbox","in":"path","required":true,"schema":{"type":"string","description":"The mailbox ADDRESS, e.g. `sales@acme.com`. Not a numeric id.","title":"Mailbox"},"description":"The mailbox ADDRESS, e.g. `sales@acme.com`. Not a numeric id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/mailboxes/{mailbox}/settings":{"patch":{"tags":["AI Inbox"],"summary":"Update Inbox Mailbox Settings","description":"Change one mailbox's inbox settings. PARTIAL: omitted fields are left alone.\n\n`auto_respond: true` LETS THE AI ANSWER REAL PEOPLE from this mailbox,\nunattended, so the operation is classified `external` (`inbox:run`) - the\nsame call already made for the LinkedIn account configuration. 404 if the\nmailbox was never connected to the inbox.","operationId":"update_inbox_mailbox_settings_inbox_mailboxes__mailbox__settings_patch","parameters":[{"name":"mailbox","in":"path","required":true,"schema":{"type":"string","description":"The mailbox ADDRESS, e.g. `sales@acme.com`. Not a numeric id.","title":"Mailbox"},"description":"The mailbox ADDRESS, e.g. `sales@acme.com`. Not a numeric id."},{"name":"provider","in":"query","required":true,"schema":{"enum":["google_mailbox","smtp"],"type":"string","description":"How the mailbox is connected. REQUIRED and not inferred: the same address can be connected either way, and guessing would act on the wrong transport. Closed to a Literal so an unknown value is a 422 naming both, rather than a `ValueError` raised inside the handler.","title":"Provider"},"description":"How the mailbox is connected. REQUIRED and not inferred: the same address can be connected either way, and guessing would act on the wrong transport. Closed to a Literal so an unknown value is a 422 naming both, rather than a `ValueError` raised inside the handler."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MailboxSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"}},"/inbox/mailboxes/{mailbox}/visibility":{"patch":{"tags":["AI Inbox"],"summary":"Set Inbox Mailbox Visibility","description":"Share a mailbox with the team, or make it personal again.\n\nTHIS CHANGES WHO CAN READ THE THREADS IN IT. Sharing exposes the\nconversation history of that mailbox to every team member; un-sharing\nhides it again, but not retroactively.\n\nONLY THE OWNER may change it - the person the mailbox was created by.\nAn API key acts as its minting human, so a key held by anyone else gets a\n403, and an org-scoped key (which owns nothing) always does.","operationId":"set_inbox_mailbox_visibility_inbox_mailboxes__mailbox__visibility_patch","parameters":[{"name":"mailbox","in":"path","required":true,"schema":{"type":"string","description":"The mailbox ADDRESS, e.g. `sales@acme.com`. Not a numeric id.","title":"Mailbox"},"description":"The mailbox ADDRESS, e.g. `sales@acme.com`. Not a numeric id."},{"name":"shared_with_team","in":"query","required":true,"schema":{"type":"boolean","description":"True makes the mailbox and its threads visible to the whole team. False makes it personal to its owner.","title":"Shared With Team"},"description":"True makes the mailbox and its threads visible to the whole team. False makes it personal to its owner."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/email-settings":{"get":{"tags":["AI Inbox"],"summary":"Get Inbox Email Settings","description":"The organisation's AI Inbox email settings.\n\nORGANISATION-WIDE - there is no per-user copy, so a change here moves the\nbehaviour for everyone. Answers `{\"message\": \"Email settings not found\"}`\nrather than 404 when nothing has been configured yet.","operationId":"get_inbox_email_settings_inbox_email_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"},"put":{"tags":["AI Inbox"],"summary":"Set Inbox Email Settings","description":"Create or replace the organisation's AI Inbox email settings.\n\nA PUT because it REPLACES: the app writes every field, so anything you\nomit is written as its default rather than left alone. Read the current\nsettings, change the one field, send the whole thing back.\n\n`business_hours_only` plus the start/end hours are what stop the AI\nreplying to a customer at 3am. `event_id` is the booking event it offers\nwhen it schedules a meeting.","operationId":"set_inbox_email_settings_inbox_email_settings_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EmailSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/email-settings/timezones":{"get":{"tags":["AI Inbox"],"summary":"List Inbox Email Settings Timezones","description":"Every timezone name `timezone` in the email settings accepts (IANA\nnames, as `items`). Static - it does not depend on the organisation.","operationId":"list_inbox_email_settings_timezones_inbox_email_settings_timezones_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxOpsListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/blocked-senders":{"get":{"tags":["AI Inbox"],"summary":"List Inbox Blocked Senders","description":"Senders the inbox refuses to ingest, per mailbox.","operationId":"list_inbox_blocked_senders_inbox_blocked_senders_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":10,"title":"Page Size"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxOpsListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"},"post":{"tags":["AI Inbox"],"summary":"Block Inbox Sender","description":"Stop a sender reaching ONE mailbox.\n\nScoped to the mailbox named in the body, not to the organisation: the same\nsender still reaches every other mailbox until blocked there too. This is\nan INGESTION filter - it is not a suppression, and it does not stop\ngraph8 emailing them (see `/contacts/suppressions` for that).","operationId":"block_inbox_sender_inbox_blocked_senders_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BlockedSenderCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/blocked-senders/{blocked_sender_id}":{"delete":{"tags":["AI Inbox"],"summary":"Unblock Inbox Sender","description":"Let a sender through again. Mail already refused is not recovered.","operationId":"unblock_inbox_sender_inbox_blocked_senders__blocked_sender_id__delete","parameters":[{"name":"blocked_sender_id","in":"path","required":true,"schema":{"type":"string","description":"Id of the block record, from `GET /inbox/blocked-senders`.","title":"Blocked Sender Id"},"description":"Id of the block record, from `GET /inbox/blocked-senders`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/inbox/emails/compose":{"post":{"tags":["AI Inbox"],"summary":"Compose Inbox Email","description":"COMPOSE AN EMAIL. WITH `save_as_draft` FALSE THIS REACHES A REAL PERSON.\n\nThe one call that does everything the compose window does:\n\n  * new thread, sent now          - `to`, `from_mailbox`, `subject`, `content`\n  * new thread, saved as a draft  - the same plus `save_as_draft: true`\n  * reply into a thread           - add `reply_to_email_id`\n  * edit an existing draft        - add `draft_id`\n  * send a draft you saved        - `draft_id` plus `save_as_draft: false`\n\n`save_as_draft` DEFAULTS TO FALSE, which means SEND. That is the app's own\ndefault and it is kept rather than made safer here, because two ends\ndisagreeing about what an omitted field does is worse than a default you\ncan read.\n\nClassified `external` (`inbox:run`) because it can deliver. Sending as a\nmailbox the caller is not authorised for is a 403 from the sender\nauthorisation gate, not a silent success - check first with\n`POST /inbox/emails/validate-mailbox`.\n\nDistinct from `POST /inbox/emails/{email_id}/send`, which can only reply\ninto a thread that already exists.","operationId":"compose_inbox_email_inbox_emails_compose_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EmailComposeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"}},"/inbox/emails/validate-mailbox":{"post":{"tags":["AI Inbox"],"summary":"Validate Inbox Send Mailbox","description":"Can this mailbox send right now? Reads only - nothing is delivered.\n\nChecks that the mailbox is connected, syncing, of a supported provider,\nthat its credentials still work, and that this caller is allowed to send\nas it. Gates on `inbox:read`: a key that can only read the inbox must\nstill be able to find out whether a send WOULD work before anyone tries.\n\nAn unauthorised mailbox is a 403 here, the same refusal the send itself\ngives, so the pre-flight and the real thing cannot disagree.","operationId":"validate_inbox_send_mailbox_inbox_emails_validate_mailbox_post","parameters":[{"name":"mailbox","in":"query","required":true,"schema":{"type":"string","description":"The mailbox address you intend to send AS.","title":"Mailbox"},"description":"The mailbox address you intend to send AS."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/emails/{email_id}/mark-read":{"post":{"tags":["AI Inbox"],"summary":"Mark Inbox Email Read","description":"Mark an email thread read. Contacts nobody.\n\nBest-effort syncs the read state up to the mail provider as well, so the customer's\nown mailbox agrees. Idempotent.\n\nGated on VISIBILITY of the owning mailbox: a personal mailbox is\nowner-only, so marking someone else's thread read is a 403 rather than a\nquiet mutation of their inbox.","operationId":"mark_inbox_email_read_inbox_emails__email_id__mark_read_post","parameters":[{"name":"email_id","in":"path","required":true,"schema":{"type":"string","description":"Email thread id.","title":"Email Id"},"description":"Email thread id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/emails/by-sequence/{sequence_id}":{"get":{"tags":["AI Inbox"],"summary":"List Inbox Emails By Sequence","description":"Email threads attributed to one sequence, newest first.\n\nA narrow projection - messages, mailbox and `updated_at` only - which is\nwhat makes it cheap enough to page through a whole campaign.\n`GET /inbox?channel=email&sequence_id=...` answers the same question with\nthe full unified thread shape; use that when you need tags and assignees.\n\nDeclared BEFORE nothing, but note the shape: `by-sequence` is a LITERAL in\nthe position `/inbox/emails/{email_id}` fills at one segment shorter, so\nthe two cannot collide.","operationId":"list_inbox_emails_by_sequence_inbox_emails_by_sequence__sequence_id__get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence (campaign) id.","title":"Sequence Id"},"description":"Sequence (campaign) id."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":10,"title":"Page Size"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxOpsListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/emails/{email_id}/sequence-candidates":{"get":{"tags":["AI Inbox"],"summary":"List Inbox Email Sequence Candidates","description":"Sequences this contact was ACTUALLY emailed from.\n\nThe only sequences `link-sequence` will accept, so read this first - it is\nthe safety guard, not a convenience. Scoping is by organisation and\ncontact; the thread id is in the path for symmetry with the link call.","operationId":"list_inbox_email_sequence_candidates_inbox_emails__email_id__sequence_candidates_get","parameters":[{"name":"email_id","in":"path","required":true,"schema":{"type":"string","description":"Email thread id.","title":"Email Id"},"description":"Email thread id."},{"name":"contact_id","in":"query","required":true,"schema":{"type":"integer","description":"Integer contact id - the CDP primary key, not an email address.","title":"Contact Id"},"description":"Integer contact id - the CDP primary key, not an email address."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxOpsListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/emails/{email_id}/link-sequence":{"post":{"tags":["AI Inbox"],"summary":"Link Inbox Email To Sequence","description":"Attach a thread to the sequence that produced it AND STOP THE SEQUENCE.\n\nThe second half is the point, not a side effect: linking tells the\nsequencer this contact replied, which halts their remaining steps. It is\nhow someone who answered stops being chased.\n\nOnly a sequence from `sequence-candidates` is accepted. If the sequencer\ncall fails the link is KEPT - the association is committed first - so a\nsuccessful response with `already_replied: false` after a provider hiccup\ncan mean the halt did not register. Re-linking is safe.","operationId":"link_inbox_email_to_sequence_inbox_emails__email_id__link_sequence_post","parameters":[{"name":"email_id","in":"path","required":true,"schema":{"type":"string","description":"Email thread id.","title":"Email Id"},"description":"Email thread id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LinkSequenceRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/emails/{email_id}/sequence":{"post":{"tags":["AI Inbox"],"summary":"Set Inbox Email Sequence","description":"Attribute a thread to a sequence, WITHOUT touching the sequencer.\n\nThe quiet twin of `link-sequence`: it re-labels the thread for reporting\nand does not tell the sequencer anything, so the contact keeps receiving\nthe remaining steps. Use `link-sequence` when someone replied.\n\nAccepts any id - unlike `link-sequence` there is no candidate check - so\na wrong value mislabels the thread silently. Gated on visibility of the\nowning mailbox.","operationId":"set_inbox_email_sequence_inbox_emails__email_id__sequence_post","parameters":[{"name":"email_id","in":"path","required":true,"schema":{"type":"string","description":"Email thread id.","title":"Email Id"},"description":"Email thread id."},{"name":"sequence_id","in":"query","required":true,"schema":{"type":"string","description":"Sequence (campaign) id to attribute the thread to.","title":"Sequence Id"},"description":"Sequence (campaign) id to attribute the thread to."},{"name":"sequence_name","in":"query","required":true,"schema":{"type":"string","description":"Display name stored alongside the id.","title":"Sequence Name"},"description":"Display name stored alongside the id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/drafts/emails/{draft_id}":{"delete":{"tags":["AI Inbox"],"summary":"Delete Inbox Email Draft","description":"Delete a saved email draft by its id, wherever it sits.\n\nNot `DELETE /inbox/emails/{email_id}/draft`, which discards the AI's\nlatest suggestion on a thread: this removes ONE draft by id, and if it was\nthe only message in its thread the thread goes too. Refused with 403 unless\nthe caller may send from the draft's mailbox - deleting a draft carries the\nsame authority as sending it. Files attached to the draft are deleted.","operationId":"delete_inbox_email_draft_inbox_drafts_emails__draft_id__delete","parameters":[{"name":"draft_id","in":"path","required":true,"schema":{"type":"string","description":"The draft's message id, from `POST /inbox/emails/compose`.","title":"Draft Id"},"description":"The draft's message id, from `POST /inbox/emails/compose`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/inbox/sms/compose":{"post":{"tags":["AI Inbox"],"summary":"Compose Inbox Sms","description":"COMPOSE AN SMS. WITH `save_as_draft` FALSE THIS REACHES A REAL PHONE.\n\nSends through the organisation's own number and files the message into the\nSMS thread, so the conversation stays in one place. `save_as_draft`\ndefaults to FALSE, which means send.\n\nClassified `external` (`inbox:run`). `from_number` must be a number this\norganisation owns - checked before anything is saved or sent, a 400\notherwise (see the module docstring for why the check lives here).","operationId":"compose_inbox_sms_inbox_sms_compose_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SmsComposeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"}},"/inbox/sms/{thread_id}/mark-read":{"post":{"tags":["AI Inbox"],"summary":"Mark Inbox Sms Read","description":"Mark an SMS thread read. Contacts nobody.\n\nAnswers 200 whether or not the thread exists - the underlying update\nmatches zero rows silently - so do not read success as proof the id was\nreal.","operationId":"mark_inbox_sms_read_inbox_sms__thread_id__mark_read_post","parameters":[{"name":"thread_id","in":"path","required":true,"schema":{"type":"string","description":"SMS thread id.","title":"Thread Id"},"description":"SMS thread id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/channels/{channel_id}":{"get":{"tags":["AI Inbox"],"summary":"Get Inbox Channel","description":"One conversation in the unified inbox shape - messages, tags and\nassignees - for any channel.\n\nThe same row `GET /inbox` lists, fetched by id. Visibility is the app's:\na thread in a personal mailbox is owner-only, so another person's key gets\na 403/404 rather than the thread.","operationId":"get_inbox_channel_inbox_channels__channel_id__get","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Conversation id.","title":"Channel Id"},"description":"Conversation id."},{"name":"channel_type","in":"query","required":true,"schema":{"enum":["email","chat","phone","sms","heyreach","meetings","support","all"],"type":"string","description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels.","title":"Channel Type"},"description":"Which channel the conversation lives in. REQUIRED: the same id means different rows in different channels."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/attachments/{token}":{"get":{"tags":["AI Inbox"],"summary":"Download Inbox Attachment","description":"Download a draft or internal-note attachment. Not enveloped: bytes are bytes.\n\nThe token only opens a file of THIS organisation: it is bound to the org\nthat uploaded it, and a token from anywhere else is a flat 404. Served\nwith `Content-Disposition: attachment` and `nosniff`, never inline.","operationId":"download_inbox_attachment_inbox_attachments__token__get","parameters":[{"name":"token","in":"path","required":true,"schema":{"type":"string","description":"The `token` returned by `POST /inbox/drafts/attachments` or `POST /inbox/notes/attachments`.","title":"Token"},"description":"The `token` returned by `POST /inbox/drafts/attachments` or `POST /inbox/notes/attachments`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"The file's bytes.","content":{"application/octet-stream":{}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/linkedin/compose":{"post":{"tags":["AI Inbox"],"summary":"Compose Inbox Linkedin Message","description":"COMPOSE A LINKEDIN MESSAGE. WITH `save_as_draft` FALSE IT REACHES A PERSON.\n\nONE DRAFT PER CONVERSATION: saving over an existing draft replaces it, and\nsending deletes whatever draft was there. `save_as_draft` defaults to\nFALSE, which means send.\n\nClassified `external` (`inbox:run`). The account must be synced and\nenabled for the inbox - check with `POST /inbox/linkedin/validate-account`.","operationId":"compose_inbox_linkedin_message_inbox_linkedin_compose_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LinkedInComposeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"}},"/inbox/linkedin/validate-account":{"post":{"tags":["AI Inbox"],"summary":"Validate Inbox Linkedin Account","description":"Can this LinkedIn account send right now? Reads only.\n\nChecks the account is synced locally, enabled for the inbox, active at the\nprovider, and that the provider credentials still authenticate. Gates on\n`inbox:read`.\n\nNOTE the app's shape, preserved here: a failure to reach the provider is\nreported as `valid: false` with an `error` string and HTTP 200, not as a\n5xx. Read `valid`, not the status code.","operationId":"validate_inbox_linkedin_account_inbox_linkedin_validate_account_post","parameters":[{"name":"linkedin_account_id","in":"query","required":true,"schema":{"type":"integer","description":"The account you intend to send from.","title":"Linkedin Account Id"},"description":"The account you intend to send from."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/linkedin/conversations/search":{"post":{"tags":["AI Inbox"],"summary":"Search Inbox Linkedin Conversations","description":"Search LinkedIn conversations across accounts.\n\nA POST because the filter is a body, not because it writes anything - it\ngates on `inbox:read`, matching `POST /inbox/chats/search` beside it.\n\n`seen: false` is the unread view. `sequence_ids` are graph8 sequence ids;\nthe handler maps them onto the provider's own campaign ids for you.","operationId":"search_inbox_linkedin_conversations_inbox_linkedin_conversations_search_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LinkedInConversationSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxOpsListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/linkedin/accounts/{account_id}/conversations/{conversation_id}":{"get":{"tags":["AI Inbox"],"summary":"Get Inbox Linkedin Conversation","description":"One LinkedIn conversation, with its whole message history.\n\nBOTH ids are required and neither is redundant: the same conversation id\ncan appear under two LinkedIn accounts, so the account is what identifies\nthe thread rather than filtering it.","operationId":"get_inbox_linkedin_conversation_inbox_linkedin_accounts__account_id__conversations__conversation_id__get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","description":"LinkedIn account id (integer).","title":"Account Id"},"description":"LinkedIn account id (integer)."},{"name":"conversation_id","in":"path","required":true,"schema":{"type":"string","description":"LinkedIn conversation id.","title":"Conversation Id"},"description":"LinkedIn conversation id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/linkedin/accounts/{account_id}/conversations/{conversation_id}/read":{"post":{"tags":["AI Inbox"],"summary":"Mark Inbox Linkedin Conversation Read","description":"Mark a LinkedIn conversation read. Contacts nobody.\n\nSyncs seen-state to whichever provider serves this organisation. The\nhandler resolves that STRICTLY on this path, so a credential-store failure\nsurfaces as an error rather than quietly toggling read state on the wrong\nprovider.","operationId":"mark_inbox_linkedin_conversation_read_inbox_linkedin_accounts__account_id__conversations__conversation_id__read_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","description":"LinkedIn account id (integer).","title":"Account Id"},"description":"LinkedIn account id (integer)."},{"name":"conversation_id","in":"path","required":true,"schema":{"type":"string","description":"LinkedIn conversation id.","title":"Conversation Id"},"description":"LinkedIn conversation id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/linkedin/accounts/{account_id}/conversations/{conversation_id}/unread":{"post":{"tags":["AI Inbox"],"summary":"Mark Inbox Linkedin Conversation Unread","description":"Put a LinkedIn conversation back in the unread queue.","operationId":"mark_inbox_linkedin_conversation_unread_inbox_linkedin_accounts__account_id__conversations__conversation_id__unread_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","description":"LinkedIn account id (integer).","title":"Account Id"},"description":"LinkedIn account id (integer)."},{"name":"conversation_id","in":"path","required":true,"schema":{"type":"string","description":"LinkedIn conversation id.","title":"Conversation Id"},"description":"LinkedIn conversation id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/linkedin/accounts":{"get":{"tags":["AI Inbox"],"summary":"List Inbox Linkedin Accounts","description":"LinkedIn accounts as the PROVIDER reports them.\n\nLive from the provider, so it reflects a disconnected or suspended account\nimmediately - but it carries none of the local inbox configuration. Read\nthe configuration back from the update call, or set it with\n`PUT /inbox/linkedin/accounts/{account_id}`.","operationId":"list_inbox_linkedin_accounts_inbox_linkedin_accounts_get","parameters":[{"name":"keyword","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by name.","title":"Keyword"},"description":"Filter by name."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxOpsListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/linkedin/accounts/{account_id}":{"put":{"tags":["AI Inbox"],"summary":"Update Inbox Linkedin Account","description":"Configure one LinkedIn account's place in the inbox.\n\nPARTIAL: only the fields you send are written, so omitting\n`auto_respond_config` leaves the existing one alone.\n\nREAD THIS BEFORE TURNING ANYTHING ON. `auto_respond: true` with\n`auto_respond_config.require_human_review: false` is the combination that\nlets the AI message real people on this account unattended - no draft, no\napproval. `require_human_review` defaults to TRUE and this route does not\nchange that; it only stops applying if you send a config that says\notherwise.","operationId":"update_inbox_linkedin_account_inbox_linkedin_accounts__account_id__put","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","description":"LinkedIn account id (integer).","title":"Account Id"},"description":"LinkedIn account id (integer)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LinkedInAccountConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"},"get":{"tags":["AI Inbox"],"summary":"Get Inbox Linkedin Account","description":"One LinkedIn account's inbox configuration - enabled, auto-respond and\nits rules, the sequence it is attributed to - plus the cached profile.\nThe read side of `PUT /inbox/linkedin/accounts/{account_id}`; 404 until the\naccount has been synced.","operationId":"get_inbox_linkedin_account_inbox_linkedin_accounts__account_id__get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","description":"LinkedIn account id (integer).","title":"Account Id"},"description":"LinkedIn account id (integer)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/linkedin/accounts/{account_id}/conversations/{conversation_id}/detail":{"get":{"tags":["AI Inbox"],"summary":"Get Inbox Linkedin Conversation Detail","description":"One LinkedIn conversation MERGED with what graph8 holds about it: the\nAI analysis, the linked contact, tags, the saved draft and assignees.\n\n`GET .../conversations/{conversation_id}` is the provider's view alone;\nthis is the view the inbox renders.","operationId":"get_inbox_linkedin_conversation_detail_inbox_linkedin_accounts__account_id__conversations__conversation_id__detail_get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","description":"LinkedIn account id (integer).","title":"Account Id"},"description":"LinkedIn account id (integer)."},{"name":"conversation_id","in":"path","required":true,"schema":{"type":"string","description":"LinkedIn conversation id.","title":"Conversation Id"},"description":"LinkedIn conversation id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/linkedin/accounts/{account_id}/conversations/{conversation_id}/draft":{"delete":{"tags":["AI Inbox"],"summary":"Delete Inbox Linkedin Draft","description":"Delete the saved draft on a LinkedIn conversation (there is at most one).\n404 when there is none. Nothing is sent.","operationId":"delete_inbox_linkedin_draft_inbox_linkedin_accounts__account_id__conversations__conversation_id__draft_delete","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","description":"LinkedIn account id (integer).","title":"Account Id"},"description":"LinkedIn account id (integer)."},{"name":"conversation_id","in":"path","required":true,"schema":{"type":"string","description":"LinkedIn conversation id.","title":"Conversation Id"},"description":"LinkedIn conversation id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/inbox/linkedin/accounts/sync":{"post":{"tags":["AI Inbox"],"summary":"Sync Inbox Linkedin Accounts","description":"Refresh the organisation's LinkedIn accounts from the provider.\n\nCreates a local configuration record for every account the provider\nreports that graph8 has not seen, and refreshes the cached profile of the\nrest. Existing configuration (enabled, auto-respond) is not changed.\nReturns the counts. Sends nothing.","operationId":"sync_inbox_linkedin_accounts_inbox_linkedin_accounts_sync_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"}},"/inbox/linkedin/accounts/{account_id}/enable":{"post":{"tags":["AI Inbox"],"summary":"Enable Inbox Linkedin Account","description":"Bring a LinkedIn account's conversations into the inbox.\n\nIf the account's configuration already has `auto_respond` on, enabling it\nis what lets the AI start messaging people from it - so this is classified\n`external`, the same tier as the configuration update.","operationId":"enable_inbox_linkedin_account_inbox_linkedin_accounts__account_id__enable_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","description":"LinkedIn account id (integer).","title":"Account Id"},"description":"LinkedIn account id (integer)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"}},"/inbox/linkedin/accounts/{account_id}/disable":{"post":{"tags":["AI Inbox"],"summary":"Disable Inbox Linkedin Account","description":"Take a LinkedIn account out of the inbox. Stops the AI answering on it;\nits configuration is kept for when it is enabled again.","operationId":"disable_inbox_linkedin_account_inbox_linkedin_accounts__account_id__disable_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"integer","description":"LinkedIn account id (integer).","title":"Account Id"},"description":"LinkedIn account id (integer)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/tags":{"post":{"tags":["AI Inbox"],"summary":"Create Inbox Tag","description":"Create an inbox tag - a conversation label, not a CRM contact tag.\n\nThe read of these objects ships as `GET /workflows/inbox-tags`. With\n`ai_can_apply` true and `rules` set, the auto-tagger may apply this tag to\nthreads on its own; with `agent_id` set, the agent answers threads carrying\nit.","operationId":"create_inbox_tag_inbox_tags_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TagCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/tags/{tag_id}":{"put":{"tags":["AI Inbox"],"summary":"Update Inbox Tag","description":"Edit an inbox tag.\n\n`/inbox/tags/...`, not `/tags/...`: `/contacts/tags` is a DIFFERENT\nvocabulary (contact tags on a CRM record) and these are conversation\nlabels. The published READ of these same objects ships as\n`GET /workflows/inbox-tags`, because the workflow builder needed it first.\n\n`ai_can_apply` and `rules` are what let the auto-tagger reach for this tag\non its own, so changing them changes what the AI does to threads nobody\nlooked at.","operationId":"update_inbox_tag_inbox_tags__tag_id__put","parameters":[{"name":"tag_id","in":"path","required":true,"schema":{"type":"string","description":"Tag id, from `GET /workflows/inbox-tags`.","title":"Tag Id"},"description":"Tag id, from `GET /workflows/inbox-tags`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TagUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"},"delete":{"tags":["AI Inbox"],"summary":"Delete Inbox Tag","description":"Delete an inbox tag. Threads lose the label; nothing else is removed.","operationId":"delete_inbox_tag_inbox_tags__tag_id__delete","parameters":[{"name":"tag_id","in":"path","required":true,"schema":{"type":"string","description":"Tag id.","title":"Tag Id"},"description":"Tag id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/inbox/tags/{tag_id}/agent":{"get":{"tags":["AI Inbox"],"summary":"Get Inbox Tag Agent","description":"Which AI agent answers threads carrying this tag.\n\nThe bridge between a label and a behaviour: tagging a thread with a tag\nthat has an agent is how that agent gets the conversation.","operationId":"get_inbox_tag_agent_inbox_tags__tag_id__agent_get","parameters":[{"name":"tag_id","in":"path","required":true,"schema":{"type":"string","description":"Tag id.","title":"Tag Id"},"description":"Tag id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/agents":{"post":{"tags":["AI Inbox"],"summary":"Create Inbox Agent","description":"Create an AI Inbox agent - the named responder tags and email settings\npoint at.\n\nNOT the Copilot Agent Runtime at `/agent/*`, which runs and approves\nautonomous work. Different object, similar name; the context notes record\nthat this pair has already misled an audit.\n\nNames are unique per organisation: a repeat is a 400, not a second agent.","operationId":"create_inbox_agent_inbox_agents_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/InboxAgentCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/drafts/attachments":{"post":{"tags":["AI Inbox"],"summary":"Upload Inbox Draft Attachment","description":"Attach a file to an existing email draft (multipart: `file`, `draft_id`).\n\nReturns `token`, `key`, `name`, `size`, `contentType`. The draft must\nalready exist and the caller must be allowed to send from its mailbox - a\n403 otherwise; 413 over 25 MB. Nothing is sent: the file rides along when\nthe draft is.\n\nCalls the app handler's own body (`__wrapped__`): the app wraps it in a\nper-process rate limiter bound to the APP's state, and this API's own\nrate limit applies instead.","operationId":"upload_inbox_draft_attachment_inbox_drafts_attachments_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"type":"object","properties":{"file":{"type":"string","format":"binary","description":"One file, up to 25 MB."},"draft_id":{"type":"string","pattern":"^[A-Za-z0-9_.:-]{1,255}$","description":"An existing draft, from `POST /inbox/emails/compose` with `save_as_draft`."}},"required":["file","draft_id"]}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/notes/attachments":{"post":{"tags":["AI Inbox"],"summary":"Upload Inbox Note Attachment","description":"Upload a file for an INTERNAL note (multipart: `file`).\n\nReturns the attachment ref (`token`, `key`, `name`, `size`,\n`contentType`) that `POST /inbox/channels/{channel_id}/comments` accepts\nin `attachments`. Notes are internal, so nothing reaches a customer.","operationId":"upload_inbox_note_attachment_inbox_notes_attachments_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"type":"object","properties":{"file":{"type":"string","format":"binary","description":"One file, up to 25 MB."}},"required":["file"]}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/drafts/generate":{"post":{"tags":["AI Inbox"],"summary":"Generate Inbox Draft","description":"Write or rewrite a message with the model. THIS SPENDS CREDITS.\n\nDELIVERS NOTHING. It returns text; sending it is a separate, `external`\ncall. Classified `billable` (`inbox:run`) because it charges - 402 when\nthe organisation has no credits left.\n\nONE CHARGE PER CALL, including a multi-operation call: pass a LIST in\n`operation` to apply several transforms in a single generation rather than\npaying per transform.\n\n`generate_from_scratch` is the only operation that does not need\n`message_html`; give it either a `conversation_id` + `channel_type` to\nground the reply in the thread, or free-text `instructions` to write\nsomething with no thread at all.\n\nWider than the already-published `GET /inbox/{reply_id}/draft`, which only\never generates from scratch on an existing thread.","operationId":"generate_inbox_draft_inbox_drafts_generate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AiDraftGenerateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"}},"/inbox/call-results/search":{"post":{"tags":["AI Inbox"],"summary":"Search Inbox Call Results","description":"Inbound call outcomes, filtered and paged. Reads only.\n\nA POST because the filter set is a body; it gates on `inbox:read`.\nFAILED calls are excluded by the handler - this is the answered-call\nrecord, not a call log.\n\nNOT `/voice/dialer/calls`, which reads the outbound dialer's own tables.\nSame-sounding feature, different rows.","operationId":"search_inbox_call_results_inbox_call_results_search_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CallResultSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxOpsListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/call-results/{call_id}":{"get":{"tags":["AI Inbox"],"summary":"Get Inbox Call Result","description":"One call outcome, with its transcript, disposition and tags.","operationId":"get_inbox_call_result_inbox_call_results__call_id__get","parameters":[{"name":"call_id","in":"path","required":true,"schema":{"type":"integer","description":"Integer call-result id.","title":"Call Id"},"description":"Integer call-result id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/reporting/bounce-classes":{"get":{"tags":["AI Inbox"],"summary":"Get Bounce Classes","description":"Delivery-failure (bounce) counts by class, mailbox or list.\n\nCounts only DSNs from mailboxes the key may see; personal-mailbox volume of other people never contributes. `list`\ngrouping additionally requires the key to see the list. No bodies, recipients or diagnostics are returned.","operationId":"get_bounce_classes_inbox_reporting_bounce_classes_get","parameters":[{"name":"since","in":"query","required":true,"schema":{"type":"string","format":"date-time","description":"Inclusive ISO-8601 timestamp WITH timezone.","title":"Since"},"description":"Inclusive ISO-8601 timestamp WITH timezone."},{"name":"group_by","in":"query","required":false,"schema":{"enum":["mailbox","list","class"],"type":"string","default":"class","title":"Group By"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/reporting/bounce-classes/sequence/{sequence_id}":{"get":{"tags":["AI Inbox"],"summary":"Get Sequence Bounce Classes","description":"Bounce-class counts for one sequence, from mailboxes the key may see. The key must be able to read the sequence.","operationId":"get_sequence_bounce_classes_inbox_reporting_bounce_classes_sequence__sequence_id__get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"since","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"description":"Optional inclusive timestamp WITH timezone; omitted means all retained events.","title":"Since"},"description":"Optional inclusive timestamp WITH timezone; omitted means all retained events."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/reporting/sequence-outcomes/{sequence_id}":{"get":{"tags":["AI Inbox"],"summary":"Get Sequence Outcomes","description":"Inbox-decided outcomes (replies, hard bounces, opt-outs) against the sequencer's contact states, distinct contacts each.\n\n404 when none of the sequence's sending mailboxes is visible to the key. `available` is false until the organisation\nhas the inbox tables.","operationId":"get_sequence_outcomes_inbox_reporting_sequence_outcomes__sequence_id__get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/{reply_id}/intent-spectrum":{"get":{"tags":["AI Inbox"],"summary":"Get Intent Spectrum","description":"The thread's buying-intent spectrum after each scored prospect message, oldest first.\n\n404 when the feature is not live for this deployment, or when the thread is missing or its mailbox is not visible to\nthe key (the same rule as the thread read).","operationId":"get_intent_spectrum_inbox__reply_id__intent_spectrum_get","parameters":[{"name":"reply_id","in":"path","required":true,"schema":{"type":"string","description":"Email thread id: the `id` of a thread returned by GET /inbox.","title":"Reply Id"},"description":"Email thread id: the `id` of a thread returned by GET /inbox."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/{reply_id}/translate":{"post":{"tags":["AI Inbox"],"summary":"Translate Thread","description":"Translate an email thread into English, cached per message. THIS SPENDS CREDITS for uncached messages.\n\nReturns cached translations plus up to 10 newly translated messages (newest first); `has_more` asks you to call again.\n404 when the thread is missing or its mailbox is not visible to the key (checked before anything is charged), 402\nwhen the organisation lacks credits, 502 when every model call in the batch failed. Delivers nothing.","operationId":"translate_thread_inbox__reply_id__translate_post","parameters":[{"name":"reply_id","in":"path","required":true,"schema":{"type":"string","description":"Email thread id: the `id` of a thread returned by GET /inbox.","title":"Reply Id"},"description":"Email thread id: the `id` of a thread returned by GET /inbox."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TranslateThreadRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"}},"/inbox/drafts/grade/config":{"get":{"tags":["AI Inbox"],"summary":"Get Grading Config","description":"Whether reply grading is `off`, `shadow` (computed, not shown) or `live` for this deployment.","operationId":"get_grading_config_inbox_drafts_grade_config_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/drafts/grade":{"post":{"tags":["AI Inbox"],"summary":"Grade Reply Draft","description":"Grade an UNSENT email reply against its thread: a label, a 0-100 score, reasons and up to two suggestions.\n\nNever charged and sends nothing. 404 when grading is off, or the thread is missing or its mailbox is not visible to the\nkey; 422 for fewer than 3 words; 503 when grading failed.","operationId":"grade_reply_draft_inbox_drafts_grade_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/GradeDraftRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/verdicts/review":{"post":{"tags":["AI Inbox"],"summary":"Review Verdict","description":"Confirm a reply verdict (link it and replan the sequence) or dismiss it without actions. Identical retries return 200.\n\nClassified `external`: confirming can re-plan what a sequence sends next. 404 when the thread, its mailbox or the verdict\nis not accessible to the key; 409 when the verdict mode is off, the resolution conflicts, nothing is pending review, or a\nconfirmation lacks a contact or sequence.","operationId":"review_verdict_inbox_verdicts_review_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VerdictReviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"}},"/inbox/whatsapp/conversations":{"post":{"tags":["AI Inbox"],"summary":"List Whatsapp Conversations","description":"WhatsApp conversations across the organisation's WhatsApp numbers, newest activity first. A read (POST for the filters).\n\nEach row names the CRM contact it is linked to. The contact's id, name and email appear only for contacts the key may\nsee; for any other the chat row is kept with those fields null (or, when `search` is used, which also matches them, the\nrow is left out). `configured: false` means the organisation has no WhatsApp numbers.","operationId":"list_whatsapp_conversations_inbox_whatsapp_conversations_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WhatsAppConversationsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/whatsapp/conversations/{chat_id}":{"get":{"tags":["AI Inbox"],"summary":"Get Whatsapp Conversation","description":"One WhatsApp conversation with its whole thread, oldest message first.\n\nThe linked contact's id, name and email are included only when the key may see that contact.","operationId":"get_whatsapp_conversation_inbox_whatsapp_conversations__chat_id__get","parameters":[{"name":"chat_id","in":"path","required":true,"schema":{"type":"string","description":"WhatsApp chat id from the conversation list.","title":"Chat Id"},"description":"WhatsApp chat id from the conversation list."},{"name":"account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"WhatsApp account id (`wa_...`).","title":"Account Id"},"description":"WhatsApp account id (`wa_...`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/whatsapp/conversations/{chat_id}/reply":{"post":{"tags":["AI Inbox"],"summary":"Reply To Whatsapp Conversation","description":"SENDS A WHATSAPP MESSAGE TO A REAL PERSON from the number that owns the chat.\n\nClassified `external` (`inbox:run`). Refused BEFORE anything is sent when the contact opted out: 409\n`contact_opted_out`, or 503 `opt_out_unverified` when the opt-out ledger cannot answer. Send a stable\n`client_message_id` so a retry of the same reply never sends twice.","operationId":"reply_to_whatsapp_conversation_inbox_whatsapp_conversations__chat_id__reply_post","parameters":[{"name":"chat_id","in":"path","required":true,"schema":{"type":"string","description":"WhatsApp chat id.","title":"Chat Id"},"description":"WhatsApp chat id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WhatsAppReplyRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"}},"/inbox/whatsapp/conversations/{chat_id}/read":{"post":{"tags":["AI Inbox"],"summary":"Mark Whatsapp Conversation Read","description":"Mark a WhatsApp chat read or unread (`read: false`). `read: true` marks it read ON WHATSAPP: the prospect may see read receipts.","operationId":"mark_whatsapp_conversation_read_inbox_whatsapp_conversations__chat_id__read_post","parameters":[{"name":"chat_id","in":"path","required":true,"schema":{"type":"string","description":"WhatsApp chat id.","title":"Chat Id"},"description":"WhatsApp chat id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WhatsAppReadRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/chats/search":{"post":{"tags":["Inbox"],"summary":"Search Inbox Chats","description":"Search and page the chat inbox.\n\nA POST because the filter is a body, not because it writes anything.\n\n`exclude_tag_ids` is the field that makes a Focused view work: the app\nsends the archived / deleted / warmup / bounced tags there. Omit it and\nthose threads come back.","operationId":"search_inbox_chats_inbox_chats_search_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ChatSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/chats/{chat_id}":{"get":{"tags":["Inbox"],"summary":"Get Inbox Chat","description":"One chat thread, with its messages.\n\nReturned whole rather than wrapped in a page: this is a single `Chat`, and\nforcing it into an `items` list would hide the thread from a caller\nreading the obvious field.","operationId":"get_inbox_chat_inbox_chats__chat_id__get","parameters":[{"name":"chat_id","in":"path","required":true,"schema":{"type":"string","description":"Chat id.","title":"Chat Id"},"description":"Chat id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/chats/{chat_id}/mark-viewed":{"post":{"tags":["Inbox"],"summary":"Mark Inbox Chat Viewed","description":"Mark a chat read. Idempotent - marking a read chat read again is a no-op.","operationId":"mark_inbox_chat_viewed_inbox_chats__chat_id__mark_viewed_post","parameters":[{"name":"chat_id","in":"path","required":true,"schema":{"type":"string","description":"Chat id.","title":"Chat Id"},"description":"Chat id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/chats/{chat_id}/star":{"put":{"tags":["Inbox"],"summary":"Star Inbox Chat","description":"SET the starred state. `is_starred` is required and is not a toggle.\n\nA toggle is not idempotent: a retried request would silently un-star the\nthread it just starred. A PUT with an explicit value is safe to retry,\nwhich is why the app models it this way and why this surface does not\n\"helpfully\" make the field optional.","operationId":"star_inbox_chat_inbox_chats__chat_id__star_put","parameters":[{"name":"chat_id","in":"path","required":true,"schema":{"type":"string","description":"Chat id.","title":"Chat Id"},"description":"Chat id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ChatStarRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/chats/auto-tag":{"post":{"tags":["Inbox"],"summary":"Auto Tag Inbox Chat","description":"Ask the model to suggest tags for a chat.\n\n`org_id` is OVERWRITTEN from the key's own principal whatever the body\nsays. The app's `ChatTaggingSuggestRequest` carries an `org_id` field\nbecause the in-app caller already knows its tenant - accepting it from a\nclient here would let a key name someone else's org in a request body.","operationId":"auto_tag_inbox_chat_inbox_chats_auto_tag_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Forwarded verbatim to the app's `ChatTaggingSuggestRequest`. Left as an open object because the tagging request shape belongs to the model that consumes it and moves with it - a frozen copy here would reject a field the app had started accepting.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/inbox/emails/search":{"post":{"tags":["Inbox"],"summary":"Search Inbox Emails","description":"Search email threads across one or more mailboxes.\n\n`mailboxes` is REQUIRED and an empty list is not \"all mailboxes\" - the\ninbox is per-mailbox, so an empty list is simply no result. Paging is on\nthe query string, matching the app, because the body is the filter.","operationId":"search_inbox_emails_inbox_emails_search_post","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":10,"title":"Page Size"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EmailSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/emails/{email_id}":{"get":{"tags":["Inbox"],"summary":"Get Inbox Email","description":"One email thread, with its messages.","operationId":"get_inbox_email_inbox_emails__email_id__get","parameters":[{"name":"email_id","in":"path","required":true,"schema":{"type":"string","description":"Email thread id.","title":"Email Id"},"description":"Email thread id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxPage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/emails/{email_id}/send":{"post":{"tags":["Inbox"],"summary":"Send Inbox Email","description":"SEND. THIS DELIVERS A REAL MESSAGE TO A REAL RECIPIENT.\n\nClassifies `external`, so it needs the `inbox:run` grant rather than plain\nwrite - a customer can hand out \"read and triage my inbox\" without handing\nout \"send as me\".\n\nPass `message_id` to keep the reply in its thread; without it the message\narrives as a new conversation.","operationId":"send_inbox_email_inbox_emails__email_id__send_post","parameters":[{"name":"email_id","in":"path","required":true,"schema":{"type":"string","description":"Email thread id.","title":"Email Id"},"description":"Email thread id."},{"name":"mailbox","in":"query","required":true,"schema":{"type":"string","description":"Mailbox address to send FROM.","title":"Mailbox"},"description":"Mailbox address to send FROM."},{"name":"provider","in":"query","required":true,"schema":{"enum":["google_mailbox","smtp"],"type":"string","description":"Required and not inferred: the same address can be connected either way, and guessing would send through the wrong transport. Declared as a Literal so an unknown value is a request-layer 422 - as a bare `str` it reached `Mailbox(provider)` inside the handler and raised a ValueError, which is a 500 on the single most consequential call on this surface.","title":"Provider"},"description":"Required and not inferred: the same address can be connected either way, and guessing would send through the wrong transport. Declared as a Literal so an unknown value is a request-layer 422 - as a bare `str` it reached `Mailbox(provider)` inside the handler and raised a ValueError, which is a 500 on the single most consequential call on this surface."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EmailSendRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"}},"/inbox/emails/{email_id}/draft":{"delete":{"tags":["Inbox"],"summary":"Discard Inbox Email Draft","description":"Throw away the AI draft on this thread.\n\nDiscards the DRAFT, not the thread - the conversation and every message\nalready sent survive. There is nothing to undo, so a UI should confirm\nbefore calling it.","operationId":"discard_inbox_email_draft_inbox_emails__email_id__draft_delete","parameters":[{"name":"email_id","in":"path","required":true,"schema":{"type":"string","description":"Email thread id.","title":"Email Id"},"description":"Email thread id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/inbox":{"get":{"tags":["Inbox"],"summary":"List Inbox","description":"List inbox threads across email, SMS, and LinkedIn channels.\n\n``status`` accepts ``SENT``, ``AI_RESPONDED`` or ``DRAFT`` (case-insensitive)\nand is forwarded to the channel handler; an unknown value returns 422.\n\nCAVEAT — ``assignee``: this cannot filter by an arbitrary email in this\nlayer. ``ChannelsService.get_channels`` only exposes ``assigned_to_me`` (a\nboolean bound to the *caller's* identity), so the value is used purely as a\ntrigger to return the caller's own assigned threads — NOT threads assigned\nto the requested email. For an org (machine) API key the caller identity is\nthe synthetic ``api-key@graph8.com``, which owns no threads, so the result\nis effectively empty. A true per-assignee filter needs an ``assignee_email``\nfield on the shared ``ChannelRequest`` (out of scope for the dev-API layer).","operationId":"list_inbox_inbox_get","parameters":[{"name":"channel","in":"query","required":false,"schema":{"anyOf":[{"$ref":"#/components/schemas/InboxChannel"},{"type":"null"}],"description":"Filter by channel: email, sms, linkedin","title":"Channel"},"description":"Filter by channel: email, sms, linkedin"},{"name":"sequence_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by sequence (campaign) ID","title":"Sequence Id"},"description":"Filter by sequence (campaign) ID"},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by status","title":"Status"},"description":"Filter by status"},{"name":"assignee","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by assignee email","title":"Assignee"},"description":"Filter by assignee email"},{"name":"tag","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by tag ID","title":"Tag"},"description":"Filter by tag ID"},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number","default":1,"title":"Page"},"description":"Page number"},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Items per page","default":50,"title":"Page Size"},"description":"Items per page"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_InboxThreadResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/hot-contacts":{"get":{"tags":["Inbox"],"summary":"Hot Contacts","description":"Most-engaged ('hot') contacts ranked by recent INBOUND interaction\nevents (replies / opens / meeting RSVPs) — NOT a static score column.\n\nOrg-scoped to the authenticated key's organization. Registered before\n`/{reply_id}` so 'hot-contacts' isn't captured as an id.","operationId":"hot_contacts_inbox_hot_contacts_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Lookback window in days","default":30,"title":"Days"},"description":"Lookback window in days"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"description":"Max contacts to return","default":10,"title":"Limit"},"description":"Max contacts to return"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_HotContactsResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/{reply_id}":{"get":{"tags":["Inbox"],"summary":"Get Reply","description":"Get a single inbox thread by ID.","operationId":"get_reply_inbox__reply_id__get","parameters":[{"name":"reply_id","in":"path","required":true,"schema":{"type":"string","description":"Thread/reply ID","title":"Reply Id"},"description":"Thread/reply ID"},{"name":"channel","in":"query","required":false,"schema":{"$ref":"#/components/schemas/InboxChannel","description":"Channel type","default":"email"},"description":"Channel type"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_InboxThreadResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/{reply_id}/assign":{"post":{"tags":["Inbox"],"summary":"Assign Reply","description":"Assign a user to an inbox thread.","operationId":"assign_reply_inbox__reply_id__assign_post","parameters":[{"name":"reply_id","in":"path","required":true,"schema":{"type":"string","description":"Thread/reply ID","title":"Reply Id"},"description":"Thread/reply ID"},{"name":"channel","in":"query","required":false,"schema":{"$ref":"#/components/schemas/InboxChannel","description":"Channel type","default":"email"},"description":"Channel type"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssignRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"}},"/inbox/{reply_id}/tag":{"post":{"tags":["Inbox"],"summary":"Tag Reply","description":"Attach tags to an inbox thread.","operationId":"tag_reply_inbox__reply_id__tag_post","parameters":[{"name":"reply_id","in":"path","required":true,"schema":{"type":"string","description":"Thread/reply ID","title":"Reply Id"},"description":"Thread/reply ID"},{"name":"channel","in":"query","required":false,"schema":{"$ref":"#/components/schemas/InboxChannel","description":"Channel type","default":"email"},"description":"Channel type"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/developer_api__interfaces__dtos__inbox__TagRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"}},"/inbox/{reply_id}/draft":{"get":{"tags":["Inbox"],"summary":"Get Draft","description":"Generate an AI draft reply. Charges credits - returns 402 on insufficient balance.","operationId":"get_draft_inbox__reply_id__draft_get","parameters":[{"name":"reply_id","in":"path","required":true,"schema":{"type":"string","description":"Thread/reply ID","title":"Reply Id"},"description":"Thread/reply ID"},{"name":"channel","in":"query","required":false,"schema":{"$ref":"#/components/schemas/InboxChannel","description":"Channel type","default":"email"},"description":"Channel type"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DraftResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/inbox/{reply_id}/send":{"post":{"tags":["Inbox"],"summary":"Send Reply","description":"Send a reply through the specified channel (email, sms, or linkedin).","operationId":"send_reply_inbox__reply_id__send_post","parameters":[{"name":"reply_id","in":"path","required":true,"schema":{"type":"string","description":"Thread/reply ID","title":"Reply Id"},"description":"Thread/reply ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SendRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SendResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"inbox:run","x-graph8-lifecycle":"active"}},"/universal-activity":{"post":{"tags":["Inbox"],"summary":"Query Universal Activity","description":"The unified activity timeline, cursor-paginated.\n\nPOST rather than GET because the filter set is large and structured -\nmatching the app, so a rebuilt inbox sends the same body.","operationId":"query_universal_activity_universal_activity_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UniversalActivityQuery"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Any_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/universal-activity/metrics":{"get":{"tags":["Inbox"],"summary":"Get Universal Activity Metrics","description":"Activity metrics for a window.\n\n`tz` is REQUIRED, deliberately: every bucket boundary is a local calendar\nday, so a default would silently bucket a customer's data in the wrong\ntimezone rather than failing loudly.","operationId":"get_universal_activity_metrics_universal_activity_metrics_get","parameters":[{"name":"tz","in":"query","required":true,"schema":{"type":"string","description":"IANA timezone name, e.g. `America/New_York`.","title":"Tz"},"description":"IANA timezone name, e.g. `America/New_York`."},{"name":"range","in":"query","required":false,"schema":{"enum":["today","yesterday","week","month","custom"],"type":"string","default":"today","title":"Range"}},{"name":"scope","in":"query","required":false,"schema":{"enum":["mine","all","team"],"type":"string","description":"`team` is accepted for back-compat; the service aliases it to `mine`.","default":"mine","title":"Scope"},"description":"`team` is accepted for back-compat; the service aliases it to `mine`."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"description":"Custom range start, inclusive, in `tz`.","title":"Start Date"},"description":"Custom range start, inclusive, in `tz`."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"description":"Custom range end, inclusive, in `tz`.","title":"End Date"},"description":"Custom range end, inclusive, in `tz`."},{"name":"workspace_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Workspace UUID; omit for org-wide.","title":"Workspace Id"},"description":"Workspace UUID; omit for org-wide."},{"name":"channel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Restrict to one channel.","title":"Channel"},"description":"Restrict to one channel."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Any_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/universal-activity/queues":{"get":{"tags":["Inbox"],"summary":"List Universal Activity Queues","description":"Queue chips.\n\nNOTE this is a stub upstream: the chips row was removed in the 2026-05-18\ndashboard pivot and the endpoint stays live only so the existing frontend\nhook keeps resolving. Exposed for shape parity - do not build on its\ncontents.","operationId":"list_universal_activity_queues_universal_activity_queues_get","parameters":[{"name":"scope","in":"query","required":false,"schema":{"enum":["mine","all","team"],"type":"string","default":"mine","title":"Scope"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Any_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/universal-activity/preview/{event_id}":{"get":{"tags":["Inbox"],"summary":"Get Universal Activity Preview","description":"Right-pane preview: email, thread and contact data for one event.\n\nApplies the same per-user mailbox privacy the app applies - the key sees\nwhat its owner sees, no more.","operationId":"get_universal_activity_preview_universal_activity_preview__event_id__get","parameters":[{"name":"event_id","in":"path","required":true,"schema":{"type":"string","description":"Activity event id.","title":"Event Id"},"description":"Activity event id."},{"name":"tabs","in":"query","required":false,"schema":{"type":"string","description":"Comma-separated tabs to hydrate.","default":"preview,thread,contact","title":"Tabs"},"description":"Comma-separated tabs to hydrate."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Any_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/universal-activity/saved-views":{"get":{"tags":["Inbox"],"summary":"List Universal Activity Saved Views","description":"Saved queue + filter combinations for this principal, plus shared ones.","operationId":"list_universal_activity_saved_views_universal_activity_saved_views_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Any_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/universal-activity/save-view":{"post":{"tags":["Inbox"],"summary":"Create Universal Activity Saved View","description":"Save a named queue + filter combination.","operationId":"create_universal_activity_saved_view_universal_activity_save_view_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SavedViewCreateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_Any_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/webchat/chat-bots":{"get":{"tags":["Web Chat"],"summary":"List Chat Bots","description":"Every chat bot in this organisation.\n\nSTART HERE. Each bot's id is the `chat_bot_id` that nearly every other\ncall on this surface requires.","operationId":"list_chat_bots_webchat_chat_bots_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"},"post":{"tags":["Web Chat"],"summary":"Create Chat Bot","description":"Create a chat bot.\n\n`agent_id` seeds the bot with an answering agent. Omitted, the bot is\ncreated with none and answers nothing until an agent is mapped with\n`POST /webchat/agents`.","operationId":"create_chat_bot_webchat_chat_bots_post","parameters":[{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string","minLength":16,"maxLength":128},{"type":"null"}],"description":"Retry-safety key for this create. Replaying the same key returns the FIRST result instead of creating a second row. Durability depends on the tenant's migration state, so treat it as best-effort.","title":"Idempotency-Key"},"description":"Retry-safety key for this create. Replaying the same key returns the FIRST result instead of creating a second row. Durability depends on the tenant's migration state, so treat it as best-effort."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ChatBotCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/webchat/chat-bots/{bot_id}":{"patch":{"tags":["Web Chat"],"summary":"Update Chat Bot","description":"Rename a chat bot. `name` is required - it is the only mutable field.","operationId":"update_chat_bot_webchat_chat_bots__bot_id__patch","parameters":[{"name":"bot_id","in":"path","required":true,"schema":{"type":"string","description":"Chat bot id (UUID).","title":"Bot Id"},"description":"Chat bot id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ChatBotUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Web Chat"],"summary":"Delete Chat Bot","description":"Delete a chat bot, and with it the content that belongs to it.\n\nDeleting the bot a live embed points at takes that widget down. Check\nwhich bot is default with `GET /webchat/chat-bots` first.","operationId":"delete_chat_bot_webchat_chat_bots__bot_id__delete","parameters":[{"name":"bot_id","in":"path","required":true,"schema":{"type":"string","description":"Chat bot id (UUID).","title":"Bot Id"},"description":"Chat bot id (UUID)."},{"name":"expected_revision","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":1},{"type":"null"}],"description":"Revision you last read. When given, a concurrent edit is a 409 instead of a silent overwrite.","title":"Expected Revision"},"description":"Revision you last read. When given, a concurrent edit is a 409 instead of a silent overwrite."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/webchat/chat-bots/{bot_id}/promote-default":{"post":{"tags":["Web Chat"],"summary":"Promote Chat Bot To Default","description":"Make this the org's DEFAULT bot.\n\nThe default is what a legacy embed snippet with no bot id resolves to, so\npromoting one CHANGES WHAT LIVE VISITORS SEE on every such page - not just\nwhat the admin shows.","operationId":"promote_chat_bot_to_default_webchat_chat_bots__bot_id__promote_default_post","parameters":[{"name":"bot_id","in":"path","required":true,"schema":{"type":"string","description":"Chat bot id (UUID).","title":"Bot Id"},"description":"Chat bot id (UUID)."},{"name":"expected_revision","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":1},{"type":"null"}],"description":"Revision you last read. When given, a concurrent edit is a 409 instead of a silent overwrite.","title":"Expected Revision"},"description":"Revision you last read. When given, a concurrent edit is a 409 instead of a silent overwrite."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/webchat/agents":{"get":{"tags":["Web Chat"],"summary":"List Webchat Agents","description":"Agent-to-URL mappings for one bot, newest first.","operationId":"list_webchat_agents_webchat_agents_get","parameters":[{"name":"chat_bot_id","in":"query","required":true,"schema":{"type":"string","description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them.","title":"Chat Bot Id"},"description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"},"post":{"tags":["Web Chat"],"summary":"Create Webchat Agent","description":"Map an agent onto the URLs it answers on.\n\n`url_filter` is matched against the page the widget is embedded on.\n`default: true` is the fallback when nothing matches - without one, a\nvisitor on an unlisted page gets no agent.","operationId":"create_webchat_agent_webchat_agents_post","parameters":[{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string","minLength":16,"maxLength":128},{"type":"null"}],"description":"Retry-safety key for this create. Replaying the same key returns the FIRST result instead of creating a second row. Durability depends on the tenant's migration state, so treat it as best-effort.","title":"Idempotency-Key"},"description":"Retry-safety key for this create. Replaying the same key returns the FIRST result instead of creating a second row. Durability depends on the tenant's migration state, so treat it as best-effort."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/webchat/agents/{agent_id}":{"patch":{"tags":["Web Chat"],"summary":"Update Webchat Agent","description":"Partial edit of an agent mapping.\n\n`chat_bot_id` is required in the body and is not a field being changed - it\nis how the row is FOUND, because agent ids are unique per bot.","operationId":"update_webchat_agent_webchat_agents__agent_id__patch","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","description":"Agent row id.","title":"Agent Id"},"description":"Agent row id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Web Chat"],"summary":"Delete Webchat Agent","description":"Remove an agent mapping. The agent itself is untouched.","operationId":"delete_webchat_agent_webchat_agents__agent_id__delete","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","description":"Agent row id.","title":"Agent Id"},"description":"Agent row id."},{"name":"chat_bot_id","in":"query","required":true,"schema":{"type":"string","description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them.","title":"Chat Bot Id"},"description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them."},{"name":"expected_revision","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":1},{"type":"null"}],"description":"Revision you last read. When given, a concurrent edit is a 409 instead of a silent overwrite.","title":"Expected Revision"},"description":"Revision you last read. When given, a concurrent edit is a 409 instead of a silent overwrite."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/webchat/buttons":{"get":{"tags":["Web Chat"],"summary":"List Webchat Buttons","description":"Quick-action buttons for one bot.","operationId":"list_webchat_buttons_webchat_buttons_get","parameters":[{"name":"chat_bot_id","in":"query","required":true,"schema":{"type":"string","description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them.","title":"Chat Bot Id"},"description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"},"post":{"tags":["Web Chat"],"summary":"Create Webchat Button","description":"Add a quick-action button.\n\n`value` is read according to `action`: a URL for `link`, the question text\nfor `question`, a calendar slug for `calendar`.","operationId":"create_webchat_button_webchat_buttons_post","parameters":[{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string","minLength":16,"maxLength":128},{"type":"null"}],"description":"Retry-safety key for this create. Replaying the same key returns the FIRST result instead of creating a second row. Durability depends on the tenant's migration state, so treat it as best-effort.","title":"Idempotency-Key"},"description":"Retry-safety key for this create. Replaying the same key returns the FIRST result instead of creating a second row. Durability depends on the tenant's migration state, so treat it as best-effort."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ButtonCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/webchat/buttons/{button_id}":{"patch":{"tags":["Web Chat"],"summary":"Update Webchat Button","description":"Partial edit of a button. `chat_bot_id` locates the row.","operationId":"update_webchat_button_webchat_buttons__button_id__patch","parameters":[{"name":"button_id","in":"path","required":true,"schema":{"type":"string","description":"Button id.","title":"Button Id"},"description":"Button id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ButtonUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Web Chat"],"summary":"Delete Webchat Button","description":"Remove a button from the widget.","operationId":"delete_webchat_button_webchat_buttons__button_id__delete","parameters":[{"name":"button_id","in":"path","required":true,"schema":{"type":"string","description":"Button id.","title":"Button Id"},"description":"Button id."},{"name":"chat_bot_id","in":"query","required":true,"schema":{"type":"string","description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them.","title":"Chat Bot Id"},"description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them."},{"name":"expected_revision","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":1},{"type":"null"}],"description":"Revision you last read. When given, a concurrent edit is a 409 instead of a silent overwrite.","title":"Expected Revision"},"description":"Revision you last read. When given, a concurrent edit is a 409 instead of a silent overwrite."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/webchat/questions":{"get":{"tags":["Web Chat"],"summary":"List Webchat Questions","description":"Preset questions for one bot.","operationId":"list_webchat_questions_webchat_questions_get","parameters":[{"name":"chat_bot_id","in":"query","required":true,"schema":{"type":"string","description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them.","title":"Chat Bot Id"},"description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"},"post":{"tags":["Web Chat"],"summary":"Create Webchat Question","description":"Offer a preset question in the widget.\n\n`placements` NULL or empty means EVERY placement, not none.","operationId":"create_webchat_question_webchat_questions_post","parameters":[{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string","minLength":16,"maxLength":128},{"type":"null"}],"description":"Retry-safety key for this create. Replaying the same key returns the FIRST result instead of creating a second row. Durability depends on the tenant's migration state, so treat it as best-effort.","title":"Idempotency-Key"},"description":"Retry-safety key for this create. Replaying the same key returns the FIRST result instead of creating a second row. Durability depends on the tenant's migration state, so treat it as best-effort."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuestionCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/webchat/questions/{question_id}":{"patch":{"tags":["Web Chat"],"summary":"Update Webchat Question","description":"Partial edit of a preset question. `chat_bot_id` locates the row.","operationId":"update_webchat_question_webchat_questions__question_id__patch","parameters":[{"name":"question_id","in":"path","required":true,"schema":{"type":"string","description":"Question id.","title":"Question Id"},"description":"Question id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuestionUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Web Chat"],"summary":"Delete Webchat Question","description":"Remove a preset question.","operationId":"delete_webchat_question_webchat_questions__question_id__delete","parameters":[{"name":"question_id","in":"path","required":true,"schema":{"type":"string","description":"Question id.","title":"Question Id"},"description":"Question id."},{"name":"chat_bot_id","in":"query","required":true,"schema":{"type":"string","description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them.","title":"Chat Bot Id"},"description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them."},{"name":"expected_revision","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":1},{"type":"null"}],"description":"Revision you last read. When given, a concurrent edit is a 409 instead of a silent overwrite.","title":"Expected Revision"},"description":"Revision you last read. When given, a concurrent edit is a 409 instead of a silent overwrite."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/webchat/blogs":{"get":{"tags":["Web Chat"],"summary":"List Webchat Blogs","description":"Article cards in the widget's rail, for one bot.","operationId":"list_webchat_blogs_webchat_blogs_get","parameters":[{"name":"chat_bot_id","in":"query","required":true,"schema":{"type":"string","description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them.","title":"Chat Bot Id"},"description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"},"post":{"tags":["Web Chat"],"summary":"Create Webchat Blog","description":"Add an article card. `display_order` is ascending; ties break newest-first.","operationId":"create_webchat_blog_webchat_blogs_post","parameters":[{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string","minLength":16,"maxLength":128},{"type":"null"}],"description":"Retry-safety key for this create. Replaying the same key returns the FIRST result instead of creating a second row. Durability depends on the tenant's migration state, so treat it as best-effort.","title":"Idempotency-Key"},"description":"Retry-safety key for this create. Replaying the same key returns the FIRST result instead of creating a second row. Durability depends on the tenant's migration state, so treat it as best-effort."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BlogCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/webchat/blogs/fetch-metadata":{"post":{"tags":["Web Chat"],"summary":"Fetch Webchat Blog Metadata","description":"Read a page's Open Graph metadata, to pre-fill an article card.\n\nFetches the URL and returns its `og:title`, `og:description` and\n`og:image`. PERSISTS NOTHING and spends nothing - create the card with\n`POST /webchat/blogs` afterwards.","operationId":"fetch_webchat_blog_metadata_webchat_blogs_fetch_metadata_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BlogMetadataRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/webchat/blogs/{blog_id}":{"patch":{"tags":["Web Chat"],"summary":"Update Webchat Blog","description":"Partial edit of an article card. `chat_bot_id` locates the row.","operationId":"update_webchat_blog_webchat_blogs__blog_id__patch","parameters":[{"name":"blog_id","in":"path","required":true,"schema":{"type":"string","description":"Article card id.","title":"Blog Id"},"description":"Article card id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BlogUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Web Chat"],"summary":"Delete Webchat Blog","description":"Remove an article card.","operationId":"delete_webchat_blog_webchat_blogs__blog_id__delete","parameters":[{"name":"blog_id","in":"path","required":true,"schema":{"type":"string","description":"Article card id.","title":"Blog Id"},"description":"Article card id."},{"name":"chat_bot_id","in":"query","required":true,"schema":{"type":"string","description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them.","title":"Chat Bot Id"},"description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them."},{"name":"expected_revision","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":1},{"type":"null"}],"description":"Revision you last read. When given, a concurrent edit is a 409 instead of a silent overwrite.","title":"Expected Revision"},"description":"Revision you last read. When given, a concurrent edit is a 409 instead of a silent overwrite."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/webchat/settings":{"get":{"tags":["Web Chat"],"summary":"Get Webchat Settings","description":"The widget's appearance and behaviour, for one bot and surface.","operationId":"get_webchat_settings_webchat_settings_get","parameters":[{"name":"chat_bot_id","in":"query","required":true,"schema":{"type":"string","description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them.","title":"Chat Bot Id"},"description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them."},{"name":"surface","in":"query","required":false,"schema":{"anyOf":[{"enum":["external","internal"],"type":"string"},{"type":"null"}],"description":"Which widget: `external` (the customer-facing embed) or `internal` (graph8's own support widget). Omitted means `external`.","title":"Surface"},"description":"Which widget: `external` (the customer-facing embed) or `internal` (graph8's own support widget). Omitted means `external`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"},"post":{"tags":["Web Chat"],"summary":"Create Webchat Settings","description":"Create the theme for one bot and surface. ONE ROW PER PAIR.\n\n409 when one already exists - use `PATCH /webchat/settings` for that.\n\nColours must be hex and dimensions must be CSS lengths; two model-level\nguards additionally refuse an illegible text/background pair and an absurd\ndesign-token magnitude. All of them run at THIS boundary, so a violation\nis a 422 naming the field.","operationId":"create_webchat_settings_webchat_settings_post","parameters":[{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string","minLength":16,"maxLength":128},{"type":"null"}],"description":"Retry-safety key for this create. Replaying the same key returns the FIRST result instead of creating a second row. Durability depends on the tenant's migration state, so treat it as best-effort.","title":"Idempotency-Key"},"description":"Retry-safety key for this create. Replaying the same key returns the FIRST result instead of creating a second row. Durability depends on the tenant's migration state, so treat it as best-effort."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SettingsCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"},"patch":{"tags":["Web Chat"],"summary":"Update Webchat Settings","description":"Partial edit of the theme. An unset field is left untouched.\n\nTHIS IS LIVE. A saved theme is what the next visitor sees, with no publish\nstep in between.\n\nTo REMOVE a design-token override, list its path in\n`themeOverridesRemove`. Sending `null` for it does not remove it - under a\npartial update that reads as \"leave it alone\".","operationId":"update_webchat_settings_webchat_settings_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SettingsUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Web Chat"],"summary":"Delete Webchat Settings","description":"Delete the theme for one bot and surface.\n\nThe widget falls back to the defaults, which is a VISIBLE change to every\nvisitor rather than a tidy-up.","operationId":"delete_webchat_settings_webchat_settings_delete","parameters":[{"name":"chat_bot_id","in":"query","required":true,"schema":{"type":"string","description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them.","title":"Chat Bot Id"},"description":"Owning chat bot id (UUID). REQUIRED: an org can run several bots and this content belongs to one of them, so it identifies the rows rather than filtering them."},{"name":"surface","in":"query","required":false,"schema":{"anyOf":[{"enum":["external","internal"],"type":"string"},{"type":"null"}],"description":"Which widget: `external` (the customer-facing embed) or `internal` (graph8's own support widget). Omitted means `external`.","title":"Surface"},"description":"Which widget: `external` (the customer-facing embed) or `internal` (graph8's own support widget). Omitted means `external`."},{"name":"expected_revision","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":1},{"type":"null"}],"description":"Revision you last read. When given, a concurrent edit is a 409 instead of a silent overwrite.","title":"Expected Revision"},"description":"Revision you last read. When given, a concurrent edit is a 409 instead of a silent overwrite."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/webchat/human-availability":{"get":{"tags":["Web Chat"],"summary":"Get Webchat Human Availability","description":"When a human is available to take a handed-off conversation.\n\nUnlike the content routes, `chat_bot_id` is OPTIONAL here: omitting it\nreads the org-wide default schedule rather than erroring.","operationId":"get_webchat_human_availability_webchat_human_availability_get","parameters":[{"name":"chat_bot_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Chat bot id. OMIT for the org-wide default schedule.","title":"Chat Bot Id"},"description":"Chat bot id. OMIT for the org-wide default schedule."},{"name":"surface","in":"query","required":false,"schema":{"anyOf":[{"enum":["external","internal"],"type":"string"},{"type":"null"}],"description":"Which widget: `external` (the customer-facing embed) or `internal` (graph8's own support widget). Omitted means `external`.","title":"Surface"},"description":"Which widget: `external` (the customer-facing embed) or `internal` (graph8's own support widget). Omitted means `external`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"},"put":{"tags":["Web Chat"],"summary":"Put Webchat Human Availability","description":"Set the office hours that decide whether a visitor is offered a person.\n\n`enabled: true` with no reachable interval is worse than off: the widget\noffers a handover nobody answers. The app refuses the unreachable shapes\nand this forwards its answer rather than inventing a second opinion.\n\nOverlapping and zero-length windows are refused at THIS boundary, because\nthe request model is the app's own.","operationId":"put_webchat_human_availability_webchat_human_availability_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/HumanAvailabilityRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/webchat/handoff-pool-status":{"get":{"tags":["Web Chat"],"summary":"Get Webchat Handoff Pool Status","description":"Whether anyone is actually in the handoff pool.\n\nThe other half of the office-hours question: a schedule can say \"open\"\nwhile the pool is empty, and this is what tells them apart.","operationId":"get_webchat_handoff_pool_status_webchat_handoff_pool_status_get","parameters":[{"name":"chat_bot_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Chat bot the widget serves; the pool is scoped per bot.","title":"Chat Bot Id"},"description":"Chat bot the widget serves; the pool is scoped per bot."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/webchat/teams":{"get":{"tags":["Web Chat"],"summary":"List Webchat Teams","description":"Scheduling teams the widget can book into.\n\nNOTE: the app's own gate docstring lists `GET /teams` among the public\nwidget-runtime routes, but the route itself carries the `webchat:read`\ngate and a `get_current_user` dependency, and has done since it was\nwritten. The CODE is authoritative and is what this mirrors; the comment is\nstale. Flagged in the PR body rather than changed here.","operationId":"list_webchat_teams_webchat_teams_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/webchat/teams/{team_id}/event-types":{"get":{"tags":["Web Chat"],"summary":"List Webchat Team Event Types","description":"Bookable event types for one team.\n\nThese are the slugs a `calendar` button's `value` refers to.","operationId":"list_webchat_team_event_types_webchat_teams__team_id__event_types_get","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","description":"Scheduling team id.","title":"Team Id"},"description":"Scheduling team id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/webchat/visitors":{"get":{"tags":["Web Chat"],"summary":"List Webchat Visitors","description":"People who used the widget, identified where possible.","operationId":"list_webchat_visitors_webchat_visitors_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":50,"title":"Page Size"}},{"name":"identified_only","in":"query","required":false,"schema":{"type":"boolean","description":"Only visitors the widget managed to identify.","default":false,"title":"Identified Only"},"description":"Only visitors the widget managed to identify."},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Search"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/webchat/visitors/funnel":{"get":{"tags":["Web Chat"],"summary":"Get Webchat Visitor Funnel","description":"Engagement funnel for the widget: per-event counts, top pages, denominators.\n\n`abandonment_window_minutes` IS NOT YET APPLIED by the app: it is validated\nand echoed back, but no number in the response depends on it. Do not build\non it expecting the figures to move. `answer_feedback` and\n`conversation_abandoned` are declared stages the app does not yet produce,\nso they are absent rather than zero.","operationId":"get_webchat_visitor_funnel_webchat_visitors_funnel_get","parameters":[{"name":"bot_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Bot Id"}},{"name":"page_url","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":2048},{"type":"null"}],"title":"Page Url"}},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO date, inclusive.","title":"Date From"},"description":"ISO date, inclusive."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO date, inclusive.","title":"Date To"},"description":"ISO date, inclusive."},{"name":"abandonment_window_minutes","in":"query","required":false,"schema":{"type":"integer","maximum":1440,"minimum":5,"description":"Validated and echoed back; not yet applied to any figure.","default":30,"title":"Abandonment Window Minutes"},"description":"Validated and echoed back; not yet applied to any figure."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/webchat/images":{"post":{"tags":["Web Chat"],"summary":"Upload Webchat Image","description":"Upload an image for the widget and get back its public URL.\n\nSTATELESS: this does not change the widget. Write the returned URL into\nthe theme with `PATCH /webchat/settings` - `headerImageUrlExternal` /\n`headerImageUrlInternal` for a header, `botAvatarCustomUrl` for an avatar.\nThe file type is checked from its bytes, not its declared content type.","operationId":"upload_webchat_image_webchat_images_post","parameters":[{"name":"purpose","in":"query","required":false,"schema":{"enum":["header","avatar"],"type":"string","description":"`header` (the widget header image) or `avatar` (the assistant avatar). Only selects where the file is stored.","default":"header","title":"Purpose"},"description":"`header` (the widget header image) or `avatar` (the assistant avatar). Only selects where the file is stored."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_webchat_image_webchat_images_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/webchat/handoff-pool":{"get":{"tags":["Web Chat"],"summary":"Get Webchat Handoff Pool","description":"The people and teams a handed-off chat can be routed to.\n\nReturns `users` and `teams`, each with the bots it is scoped to (an empty\n`chat_bot_ids` means every bot). An EMPTY pool is not \"nobody\": it means\nthe app falls back to its default round-robin.","operationId":"get_webchat_handoff_pool_webchat_handoff_pool_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"}},"/webchat/handoff-pool/users":{"post":{"tags":["Web Chat"],"summary":"Add Webchat Handoff Pool Users","description":"Add people to the handoff pool. Returns the whole pool afterwards.\n\nAdding someone already in it is a no-op, not an error. From the first\nmember on, handed-off chats go ONLY to the pool.","operationId":"add_webchat_handoff_pool_users_webchat_handoff_pool_users_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/HandoffPoolUsersRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/webchat/handoff-pool/teams":{"post":{"tags":["Web Chat"],"summary":"Add Webchat Handoff Pool Teams","description":"Add whole teams to the handoff pool. Returns the whole pool afterwards.\n\nA team's members are expanded when a chat is routed, so someone joining\nthe team later is reachable without another call.","operationId":"add_webchat_handoff_pool_teams_webchat_handoff_pool_teams_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/HandoffPoolTeamsRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/webchat/handoff-pool/users/{user_id}":{"delete":{"tags":["Web Chat"],"summary":"Remove Webchat Handoff Pool User","description":"Take a person out of the handoff pool. 404 if they are not in it.","operationId":"remove_webchat_handoff_pool_user_webchat_handoff_pool_users__user_id__delete","parameters":[{"name":"user_id","in":"path","required":true,"schema":{"type":"string","description":"Member user id.","title":"User Id"},"description":"Member user id."},{"name":"pool","in":"query","required":false,"schema":{"anyOf":[{"enum":["external","internal"],"type":"string"},{"type":"null"}],"description":"Only the row in this pool. Omitted removes the person or team from every pool. `internal` is graph8's own support widget.","title":"Pool"},"description":"Only the row in this pool. Omitted removes the person or team from every pool. `internal` is graph8's own support widget."},{"name":"chat_bot_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"description":"Only the row scoped to this chat bot. Omitted removes it across every bot.","title":"Chat Bot Id"},"description":"Only the row scoped to this chat bot. Omitted removes it across every bot."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/webchat/handoff-pool/teams/{team_id}":{"delete":{"tags":["Web Chat"],"summary":"Remove Webchat Handoff Pool Team","description":"Take a team out of the handoff pool. 404 if it is not in it.","operationId":"remove_webchat_handoff_pool_team_webchat_handoff_pool_teams__team_id__delete","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"pool","in":"query","required":false,"schema":{"anyOf":[{"enum":["external","internal"],"type":"string"},{"type":"null"}],"description":"Only the row in this pool. Omitted removes the person or team from every pool. `internal` is graph8's own support widget.","title":"Pool"},"description":"Only the row in this pool. Omitted removes the person or team from every pool. `internal` is graph8's own support widget."},{"name":"chat_bot_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"description":"Only the row scoped to this chat bot. Omitted removes it across every bot.","title":"Chat Bot Id"},"description":"Only the row scoped to this chat bot. Omitted removes it across every bot."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/webchat/handoff-pool/users/{user_id}/scope":{"patch":{"tags":["Web Chat"],"summary":"Update Webchat Handoff Pool User Scope","description":"REPLACE which bots a person takes handoffs for. Empty list = every bot.\n\nA replace, not a merge: bots left out of the list are dropped.","operationId":"update_webchat_handoff_pool_user_scope_webchat_handoff_pool_users__user_id__scope_patch","parameters":[{"name":"user_id","in":"path","required":true,"schema":{"type":"string","description":"Member user id.","title":"User Id"},"description":"Member user id."},{"name":"pool","in":"query","required":false,"schema":{"enum":["external","internal"],"type":"string","description":"Pool to re-scope. Only `external` is accepted by the app: the internal pool is not per-bot.","default":"external","title":"Pool"},"description":"Pool to re-scope. Only `external` is accepted by the app: the internal pool is not per-bot."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/HandoffPoolScopeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/webchat/handoff-pool/teams/{team_id}/scope":{"patch":{"tags":["Web Chat"],"summary":"Update Webchat Handoff Pool Team Scope","description":"REPLACE which bots a team takes handoffs for. Empty list = every bot.","operationId":"update_webchat_handoff_pool_team_scope_webchat_handoff_pool_teams__team_id__scope_patch","parameters":[{"name":"team_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Team id (UUID).","title":"Team Id"},"description":"Team id (UUID)."},{"name":"pool","in":"query","required":false,"schema":{"enum":["external","internal"],"type":"string","description":"Pool to re-scope. Only `external` is accepted by the app: the internal pool is not per-bot.","default":"external","title":"Pool"},"description":"Pool to re-scope. Only `external` is accepted by the app: the internal pool is not per-bot."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/HandoffPoolScopeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/webchat/assessments":{"get":{"tags":["Web Chat"],"summary":"List Assessments","description":"Assessments in this organisation.","operationId":"list_assessments_webchat_assessments_get","parameters":[{"name":"chat_bot_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter to one bot. OPTIONAL here, unlike the other webchat content routes - omitted returns every assessment in the org.","title":"Chat Bot Id"},"description":"Filter to one bot. OPTIONAL here, unlike the other webchat content routes - omitted returns every assessment in the org."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"},"post":{"tags":["Web Chat"],"summary":"Create Assessment","description":"Create an assessment.\n\n`definition` is the flow itself and is validated HERE, against the app's\nown model - so a graph whose `start_step_id` names a step it does not\ndefine is a 422 rather than a dead end a visitor walks into.\n\nNote `chat_bot_id` is a QUERY parameter on this one and a BODY field on\nevery other webchat create. That is the app's own inconsistency, mirrored\nrather than tidied: moving it into the body would send the handler a\nparameter it does not take.","operationId":"create_assessment_webchat_assessments_post","parameters":[{"name":"chat_bot_id","in":"query","required":true,"schema":{"type":"string","description":"Owning chat bot id (UUID).","title":"Chat Bot Id"},"description":"Owning chat bot id (UUID)."},{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying it returns the FIRST result.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying it returns the FIRST result."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssessmentCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"}},"/webchat/assessments/{assessment_id}":{"get":{"tags":["Web Chat"],"summary":"Get Assessment","description":"One assessment, with its full question graph.","operationId":"get_assessment_webchat_assessments__assessment_id__get","parameters":[{"name":"assessment_id","in":"path","required":true,"schema":{"type":"string","description":"Assessment id.","title":"Assessment Id"},"description":"Assessment id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"inbox:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Web Chat"],"summary":"Update Assessment","description":"Partial edit of an assessment.\n\n`active: false` takes it out of the widget without deleting it, which is\nthe reversible way to retire one.\n\nThe concurrency field is `revision` here, not `expected_revision`. That is\nthe app's spelling on this model alone and is mirrored deliberately - a\ntidier name would be a field the handler does not read, silently switching\nthe check off.","operationId":"update_assessment_webchat_assessments__assessment_id__patch","parameters":[{"name":"assessment_id","in":"path","required":true,"schema":{"type":"string","description":"Assessment id.","title":"Assessment Id"},"description":"Assessment id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AssessmentUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"inbox:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Web Chat"],"summary":"Delete Assessment","description":"Delete an assessment permanently.\n\nSessions already taken against it are historical records and are not\nrewritten. To retire one reversibly, PATCH it with `active: false`.","operationId":"delete_assessment_webchat_assessments__assessment_id__delete","parameters":[{"name":"assessment_id","in":"path","required":true,"schema":{"type":"string","description":"Assessment id.","title":"Assessment Id"},"description":"Assessment id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WebchatPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"inbox:delete","x-graph8-lifecycle":"active"}},"/audience-syncs/accounts":{"get":{"tags":["Integrations"],"summary":"List Ad Accounts","description":"Ad accounts this org can sync audiences into.\n\nOne row per connected account across Google, Meta, LinkedIn and X. The\n`ad_account_id` values here are what a sync config targets.","operationId":"list_ad_accounts_audience_syncs_accounts_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/audience-syncs/account-health":{"get":{"tags":["Integrations"],"summary":"List Ad Account Health","description":"Whether each connected ad account is still authorised and usable.\n\nReads the verdict the hourly poller recorded; it deliberately makes NO live\nplatform call, so it is cheap enough to poll and can be up to an hour\nstale. This is the endpoint that answers \"why did my sync stop working\" -\nusually a revoked token or a suspended account.","operationId":"list_ad_account_health_audience_syncs_account_health_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/audience-syncs/platforms":{"get":{"tags":["Integrations"],"summary":"List Ad Platforms","description":"Which ad platforms are connected, and how many syncs each carries.\n\nReads graph8's own integration rows rather than calling any platform, so a\nplatform can read \"connected\" here and still be unhealthy - check\n`/account-health` for that.","operationId":"list_ad_platforms_audience_syncs_platforms_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/audience-syncs/x/account-options":{"get":{"tags":["Integrations"],"summary":"Get X Account Options","description":"The ad accounts, payment methods and promotable users the organization's X login can use, and the current choice.\n\nAn X-side problem (not connected, expired login, no ad access) is NOT an HTTP error: it comes back as\n`error: {code, message}` beside whatever could be read, so a UI can show it. `refresh=true` asks X again and counts\nagainst X's own per-app rate limit, so it is limited to 20 per minute per organization (429 beyond that).","operationId":"get_x_account_options_audience_syncs_x_account_options_get","parameters":[{"name":"refresh","in":"query","required":false,"schema":{"type":"boolean","description":"Ask X again instead of using the few-minute cache.","default":false,"title":"Refresh"},"description":"Ask X again instead of using the few-minute cache."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/audience-syncs/x/account-selection":{"put":{"tags":["Integrations"],"summary":"Put X Account Selection","description":"Choose the X ad account (and payment method) new X campaigns launch into.\n\nCHANGES WHERE FUTURE X SPEND IS BILLED. The choice is validated against what the X login can actually reach: 400 for\nan account or a payment method it cannot use, 404 when X is not connected, 503 when X cannot be asked right now.\nExisting campaigns are untouched; the next save of an existing X sync config picks the new choice up. Limited to 10\nper minute per organization.","operationId":"put_x_account_selection_audience_syncs_x_account_selection_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/XAccountSelectionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/audience-syncs/analytics/summary":{"get":{"tags":["Integrations"],"summary":"Get Ad Analytics Summary","description":"Spend, impressions, clicks and conversions across every ad account.","operationId":"get_ad_analytics_summary_audience_syncs_analytics_summary_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Days to look back.","default":30,"title":"Days"},"description":"Days to look back."},{"name":"platform","in":"query","required":false,"schema":{"anyOf":[{"enum":["meta","linkedin","google","x"],"type":"string"},{"type":"null"}],"description":"One platform. Omit for all.","title":"Platform"},"description":"One platform. Omit for all."},{"name":"ad_account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Ad Account Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/audience-syncs/analytics/daily-trend":{"get":{"tags":["Integrations"],"summary":"Get Ad Daily Trend","description":"The same numbers, one row per day.","operationId":"get_ad_daily_trend_audience_syncs_analytics_daily_trend_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Days to look back.","default":30,"title":"Days"},"description":"Days to look back."},{"name":"platform","in":"query","required":false,"schema":{"anyOf":[{"enum":["meta","linkedin","google","x"],"type":"string"},{"type":"null"}],"description":"One platform. Omit for all.","title":"Platform"},"description":"One platform. Omit for all."},{"name":"sync_config_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Scope to one sync config.","title":"Sync Config Id"},"description":"Scope to one sync config."},{"name":"ad_account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Ad Account Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/audience-syncs/{config_id}/analytics":{"get":{"tags":["Integrations"],"summary":"Get Sync Config Analytics","description":"What the campaigns behind ONE sync config produced.","operationId":"get_sync_config_analytics_audience_syncs__config_id__analytics_get","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"integer","description":"The sync config's id.","title":"Config Id"},"description":"The sync config's id."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Days to look back.","default":30,"title":"Days"},"description":"Days to look back."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/audience-syncs/{config_id}/segment-status":{"get":{"tags":["Integrations"],"summary":"Get Sync Segment Status","description":"Whether the platform has finished BUILDING the audience.\n\nA LIVE platform read, unlike `/account-health`. Matched audiences are not\nusable the moment they are uploaded - the platform matches and sizes them\nfirst, and a campaign pointed at one that is still building serves nothing.\nThis is the endpoint that explains that silence.","operationId":"get_sync_segment_status_audience_syncs__config_id__segment_status_get","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"integer","description":"The sync config's id.","title":"Config Id"},"description":"The sync config's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/audience-syncs/{config_id}/draft":{"delete":{"tags":["Integrations"],"summary":"Discard Draft Sync Config","description":"Throw away a sync config that was never launched.\n\nREFUSED with a 409 once any campaign on it has a platform id - at that\npoint there is live platform state that discarding would orphan. Use\n`DELETE /audience-syncs/{config_id}` for a config that has launched.","operationId":"discard_draft_sync_config_audience_syncs__config_id__draft_delete","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"integer","description":"The sync config's id.","title":"Config Id"},"description":"The sync config's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"integrations:delete","x-graph8-lifecycle":"active"}},"/audience-syncs/google/conversion-tracking":{"get":{"tags":["Integrations"],"summary":"Get Google Conversion Tracking","description":"Whether this Google Ads account has any active conversion action.\n\nWith none, Smart Bidding has nothing to optimise towards and a Demand Gen\nor Performance Max campaign spends without learning. A live Google read.\n\nAn `ad_account_id` the org does not own is a 403, not an empty result.","operationId":"get_google_conversion_tracking_audience_syncs_google_conversion_tracking_get","parameters":[{"name":"ad_account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"A Google Ads customer id. Omit to use the org's own.","title":"Ad Account Id"},"description":"A Google Ads customer id. Omit to use the org's own."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/audience-syncs/google/conversion-actions":{"post":{"tags":["Integrations"],"summary":"Create Google Conversion Action","description":"Create a conversion action ON THE CUSTOMER'S GOOGLE ADS ACCOUNT.\n\nIDEMPOTENT: an action with the same name is reused rather than duplicated,\nso this is safe to call before every launch. An empty body provisions the\ndefault primary landing-page action - the same one a Demand Gen or\nPerformance Max launch provisions for itself.","operationId":"create_google_conversion_action_audience_syncs_google_conversion_actions_post","parameters":[{"name":"ad_account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Ad Account Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/CreateConversionActionRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/audience-syncs/google/conversions":{"post":{"tags":["Integrations"],"summary":"Upload Google Conversions","description":"Upload offline conversions to Google Ads.\n\nIRREVERSIBLE once `dry_run=false`: a conversion recorded against the wrong\naction cannot be unrecorded, and Smart Bidding immediately starts\noptimising the customer's budget against it. The safe default and the\n`validate_only` middle step are both preserved from the app rather than\nflattened into \"do the thing\".","operationId":"upload_google_conversions_audience_syncs_google_conversions_post","parameters":[{"name":"ad_account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Ad Account Id"}},{"name":"dry_run","in":"query","required":false,"schema":{"type":"boolean","description":"TRUE BY DEFAULT, and deliberately. The batch is built and NOTHING is sent to Google. Read the result, then send `false`.","default":true,"title":"Dry Run"},"description":"TRUE BY DEFAULT, and deliberately. The batch is built and NOTHING is sent to Google. Read the result, then send `false`."},{"name":"validate_only","in":"query","required":false,"schema":{"type":"boolean","description":"With `dry_run=false`, ask Google to VALIDATE the batch without recording it. The middle step between a local preview and a real upload - it catches what only Google can tell you.","default":false,"title":"Validate Only"},"description":"With `dry_run=false`, ask Google to VALIDATE the batch without recording it. The middle step between a local preview and a real upload - it catches what only Google can tell you."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":2000,"minimum":1,"description":"Conversions per call.","default":200,"title":"Limit"},"description":"Conversions per call."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/audience-syncs/google/video-assets":{"get":{"tags":["Integrations"],"summary":"List Video Assets","description":"Videos registered for use in Google Video campaigns.","operationId":"list_video_assets_audience_syncs_google_video_assets_get","parameters":[{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"enum":["link","upload","studio"],"type":"string"},{"type":"null"}],"description":"Omit for every source.","title":"Source"},"description":"Omit for every source."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/audience-syncs/google/video-assets/{asset_id}":{"get":{"tags":["Integrations"],"summary":"Get Video Asset","description":"One video asset, including how far its upload to YouTube has got.","operationId":"get_video_asset_audience_syncs_google_video_assets__asset_id__get","parameters":[{"name":"asset_id","in":"path","required":true,"schema":{"type":"integer","description":"The video asset's id.","title":"Asset Id"},"description":"The video asset's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/audience-syncs/google/video-assets/links":{"post":{"tags":["Integrations"],"summary":"Register Video Asset From Link","description":"Register a YouTube video by URL.\n\nThe URL is validated against YouTube, so a private or deleted video is\nrefused here rather than at launch. Rate limited to 20 per minute per org\nby the app's own limiter, per org - over it, a 429.","operationId":"register_video_asset_from_link_audience_syncs_google_video_assets_links_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateVideoAssetFromLinkRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/audience-syncs/google/video-assets/library":{"post":{"tags":["Integrations"],"summary":"Register Video Asset From Library","description":"Queue a Studio library video for upload to YouTube.\n\n202: the upload to YouTube happens in a worker afterwards, so the asset is\nnot usable in a campaign the moment this returns. Poll\n`GET /audience-syncs/google/video-assets/{asset_id}`.\n\nRate limited to 30 per minute per org by the app's own limiter.","operationId":"register_video_asset_from_library_audience_syncs_google_video_assets_library_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RegisterLibraryVideoAssetRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/audience-syncs/google/video-assets/upload-urls":{"post":{"tags":["Integrations"],"summary":"Create Video Upload Url","description":"Step 1 of 2 of a video upload: a presigned PUT for the file itself.\n\nPUT the bytes to the returned URL - straight to storage, not through graph8\n- with exactly `size_bytes` of body and the `content_type` given here; both\nare signed into the URL and a mismatch is refused. Then register the\nreturned `key` with `POST /audience-syncs/google/video-assets/uploads`.\n\n503 when upload storage is not configured. Rate limited to 20 per minute\nper org.","operationId":"create_video_upload_url_audience_syncs_google_video_assets_upload_urls_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateVideoUploadUrlRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/audience-syncs/google/video-assets/uploads":{"post":{"tags":["Integrations"],"summary":"Register Uploaded Video Asset","description":"Step 2 of 2: register the uploaded file for the YouTube upload worker.\n\nThe object is re-checked server-side (size and type) before it is queued.\n202: YouTube processing happens afterwards - poll\n`GET /audience-syncs/google/video-assets/{asset_id}` until it is usable.\nRate limited to 30 per minute per org.","operationId":"register_uploaded_video_asset_audience_syncs_google_video_assets_uploads_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RegisterVideoAssetRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/audience-syncs":{"get":{"tags":["Audience Syncs"],"summary":"List Audience Syncs","description":"List all audience sync configurations for the org.","operationId":"list_audience_syncs_audience_syncs_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_AudienceSyncConfigResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"},"post":{"tags":["Audience Syncs"],"summary":"Create Audience Sync","description":"Create a new audience sync configuration.","operationId":"create_audience_sync_audience_syncs_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AudienceSyncCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AudienceSyncConfigResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/audience-syncs/{config_id}":{"get":{"tags":["Audience Syncs"],"summary":"Get Audience Sync","description":"Get a sync configuration by ID.","operationId":"get_audience_sync_audience_syncs__config_id__get","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"integer","description":"Sync config ID","title":"Config Id"},"description":"Sync config ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AudienceSyncConfigResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Audience Syncs"],"summary":"Update Audience Sync","description":"Update a sync configuration (partial update).","operationId":"update_audience_sync_audience_syncs__config_id__patch","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"integer","description":"Sync config ID","title":"Config Id"},"description":"Sync config ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AudienceSyncUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AudienceSyncConfigResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Audience Syncs"],"summary":"Delete Audience Sync","description":"Soft delete a sync configuration.","operationId":"delete_audience_sync_audience_syncs__config_id__delete","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"integer","description":"Sync config ID","title":"Config Id"},"description":"Sync config ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"integrations:delete","x-graph8-lifecycle":"active"}},"/audience-syncs/{config_id}/trigger":{"post":{"tags":["Audience Syncs"],"summary":"Trigger Audience Sync","description":"Manually trigger an audience sync.","operationId":"trigger_audience_sync_audience_syncs__config_id__trigger_post","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"integer","description":"Sync config ID","title":"Config Id"},"description":"Sync config ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/audience-syncs/{config_id}/runs":{"get":{"tags":["Audience Syncs"],"summary":"List Sync Runs","description":"Get sync run history for a configuration.","operationId":"list_sync_runs_audience_syncs__config_id__runs_get","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"integer","description":"Sync config ID","title":"Config Id"},"description":"Sync config ID"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Max runs to return","default":20,"title":"Limit"},"description":"Max runs to return"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_SyncRunResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/audience-syncs/{config_id}/errors":{"get":{"tags":["Audience Syncs"],"summary":"List Sync Errors","description":"Get sync error logs for a configuration.","operationId":"list_sync_errors_audience_syncs__config_id__errors_get","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"integer","description":"Sync config ID","title":"Config Id"},"description":"Sync config ID"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Max errors to return","default":20,"title":"Limit"},"description":"Max errors to return"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_SyncErrorResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/ad-campaigns/metrics":{"get":{"tags":["Ad Campaigns"],"summary":"Get Per Campaign Metrics","description":"Spend and performance broken down per campaign.\n\nA two-segment LITERAL under a prefix that already has\n`GET /ad-campaigns/{campaign_id}` typed `int`, so this router is included\nfirst. The app's own router carries a comment about this exact endpoint\nbeing shadowed once already.","operationId":"get_per_campaign_metrics_ad_campaigns_metrics_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Days to look back.","default":30,"title":"Days"},"description":"Days to look back."},{"name":"platform","in":"query","required":false,"schema":{"anyOf":[{"enum":["meta","linkedin","google","x"],"type":"string"},{"type":"null"}],"description":"One platform. Omit for all.","title":"Platform"},"description":"One platform. Omit for all."},{"name":"ad_account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Ad Account Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"ads:read","x-graph8-lifecycle":"active"}},"/ad-campaigns/status-refresh":{"post":{"tags":["Ad Campaigns"],"summary":"Refresh All Campaign Statuses","description":"Re-read every refreshable campaign's review state from its platform.\n\n504 if the platforms take too long; the campaigns that did refresh keep\ntheir new state, so a retry is safe and picks up where it stopped.","operationId":"refresh_all_campaign_statuses_ad_campaigns_status_refresh_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"ads:run","x-graph8-lifecycle":"active"}},"/ad-campaigns/{campaign_id}/editable":{"get":{"tags":["Ad Campaigns"],"summary":"Get Campaign Editable Fields","description":"Which of this campaign's fields the platform will actually let you change.\n\nPlatform- and state-dependent: a live Google Search campaign accepts a\nbudget change and refuses a channel change, and a campaign in review\naccepts almost nothing. Read this before attempting an edit.\n\nGated on `ads:launch` rather than `ads:view`, as the app gates it: it\ndescribes the money controls, and the app treats that whole surface as one\npermission.","operationId":"get_campaign_editable_fields_ad_campaigns__campaign_id__editable_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"The ad campaign's id.","title":"Campaign Id"},"description":"The ad campaign's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"ads:read","x-graph8-lifecycle":"active"}},"/ad-campaigns/{campaign_id}/retry":{"post":{"tags":["Ad Campaigns"],"summary":"Retry Campaign Launch","description":"Re-attempt a launch that failed or stalled.\n\nTHIS SPENDS THE CUSTOMER'S ADVERTISING BUDGET when it succeeds - the\ncampaign goes live on the platform with the budget it was created with.\nLike the launch, a refusal comes back as a 200 whose body `status` is\n`error` - read it. Check `GET /ad-campaigns/{campaign_id}` first: a\ncampaign that is already live does not need this, and retrying one whose\ncreative was rejected will fail the same way until the creative changes.","operationId":"retry_campaign_launch_ad_campaigns__campaign_id__retry_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"The ad campaign's id.","title":"Campaign Id"},"description":"The ad campaign's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"ads:run","x-graph8-lifecycle":"active"}},"/ad-campaigns/{campaign_id}/status-refresh":{"post":{"tags":["Ad Campaigns"],"summary":"Refresh Campaign Status","description":"Re-read one campaign's review state from its platform.\n\nPolicy review is ASYNCHRONOUS: a creative can be auto-rejected minutes\nafter the platform accepted the campaign, and graph8's copy still says it\nlaunched. This promotes the platform's real state - `REJECTED`,\n`NEEDS_REVIEW` - into it. A live platform read; nothing is changed on the\nplatform.","operationId":"refresh_campaign_status_ad_campaigns__campaign_id__status_refresh_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"The ad campaign's id.","title":"Campaign Id"},"description":"The ad campaign's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"ads:run","x-graph8-lifecycle":"active"}},"/ad-campaigns/{campaign_id}":{"delete":{"tags":["Ad Campaigns"],"summary":"Delete Ad Campaign","description":"Stop and remove a campaign.\n\nTHIS STOPS A LIVE CAMPAIGN ON THE PLATFORM FIRST, then removes graph8's\nrow. There is no undo: the platform-side removal is the platform's, and the\ncampaign's history goes with the local row.\n\n502 - not 404 - when the platform refuses the removal, because the campaign\nis then still LIVE AND SPENDING and reporting success would be the worst\npossible answer.","operationId":"delete_ad_campaign_ad_campaigns__campaign_id__delete","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"The ad campaign's id.","title":"Campaign Id"},"description":"The ad campaign's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"ads:delete","x-graph8-lifecycle":"active"},"put":{"tags":["Ad Campaigns"],"summary":"Update Ad Campaign","description":"Edit a LIVE campaign: budget, schedule, creative, keywords, ad copy,\ntargeting, pause or resume.\n\nOmitted fields are left alone; an unknown field is a 422 (the app's model\nforbids extras, so a typo cannot silently do nothing). Read\n`GET /ad-campaigns/{campaign_id}/editable` first - the platform refuses\nsome changes on some campaign types and states.\n\nA 200 is NOT blanket success: the response `status` is `partial` whenever\nany single change failed, and `changes[]` says which.","operationId":"update_ad_campaign_ad_campaigns__campaign_id__put","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"The ad campaign's id.","title":"Campaign Id"},"description":"The ad campaign's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateAdCampaignRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"ads:run","x-graph8-lifecycle":"active"},"get":{"tags":["Ad Campaigns"],"summary":"Get Ad Campaign","description":"Fetch one paid ad campaign.","operationId":"get_ad_campaign_ad_campaigns__campaign_id__get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"Ad campaign ID","title":"Campaign Id"},"description":"Ad campaign ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdCampaignResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"ads:read","x-graph8-lifecycle":"active"}},"/ad-campaigns/images":{"post":{"tags":["Ad Campaigns"],"summary":"Upload Ad Image","description":"Upload an ad creative image and get back the public URL a launch takes.\n\nThe app's own checks run unchanged: 10 MB, and the file's MAGIC BYTES decide\nits type rather than its name or declared content type. SVG is refused with\na 422 - no ad platform accepts it; rasterise first.","operationId":"upload_ad_image_ad_campaigns_images_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_ad_image_ad_campaigns_images_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"ads:run","x-graph8-lifecycle":"active"}},"/audience-syncs/{config_id}/launch":{"post":{"tags":["Ad Campaigns"],"summary":"Launch Ad Campaign","description":"Launch a paid campaign on the platform, targeting this sync's audience.\n\nTHIS SPENDS THE CUSTOMER'S ADVERTISING BUDGET. The campaign goes live with\n`daily_budget` in `currency` from `start_date`, and the platform starts\ncharging as soon as it serves. `spend_cap` and `auto_pause_at` are the\nguard rails; set them. Upload the creative first with\n`POST /ad-campaigns/images`.\n\nREAD `status` IN THE BODY. The app answers a refused launch (campaign not\nfound, the platform rejecting it) with a 200 whose `status` is `error`, and\nthis route passes that through unchanged rather than guessing an HTTP code\nfor it. A launch can also partly succeed - the platform accepts the campaign\nand then rejects a creative in review - so follow up with\n`POST /ad-campaigns/{campaign_id}/status-refresh`.","operationId":"launch_ad_campaign_audience_syncs__config_id__launch_post","parameters":[{"name":"config_id","in":"path","required":true,"schema":{"type":"integer","description":"The sync config whose audience the campaign targets.","title":"Config Id"},"description":"The sync config whose audience the campaign targets."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LaunchAdCampaignRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"ads:run","x-graph8-lifecycle":"active"}},"/ad-campaigns/{campaign_id}/edit-preview":{"post":{"tags":["Ad Campaigns"],"summary":"Preview Ad Campaign Edit","description":"What an edit WOULD change, without applying any of it.\n\nSame body and same response shape as `PUT /ad-campaigns/{campaign_id}`.\nReads the campaign's live platform state to diff against and changes\nnothing. Run it first: some changes restart the platform's learning phase.","operationId":"preview_ad_campaign_edit_ad_campaigns__campaign_id__edit_preview_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"The ad campaign's id.","title":"Campaign Id"},"description":"The ad campaign's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateAdCampaignRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"ads:run","x-graph8-lifecycle":"active"}},"/ad-campaigns":{"get":{"tags":["Ad Campaigns"],"summary":"List Ad Campaigns","description":"List the org's paid ad campaigns.","operationId":"list_ad_campaigns_ad_campaigns_get","parameters":[{"name":"platform","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by platform: google | linkedin","title":"Platform"},"description":"Filter by platform: google | linkedin"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_AdCampaignResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"ads:read","x-graph8-lifecycle":"active"}},"/ad-campaigns/{campaign_id}/ads":{"get":{"tags":["Ad Campaigns"],"summary":"List Campaign Ads","description":"List the ads in a campaign.\n\nAlways a collection. A campaign launched before per-ad control existed\nreturns its single implicit ad, promoted to a real slot on first read so the\ncaller receives a stable id it can act on.","operationId":"list_campaign_ads_ad_campaigns__campaign_id__ads_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"Ad campaign ID","title":"Campaign Id"},"description":"Ad campaign ID"},{"name":"include_archived","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Include Archived"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"ads:read","x-graph8-lifecycle":"active"},"post":{"tags":["Ad Campaigns"],"summary":"Create Campaign Ad","description":"Add an ad to a campaign.\n\nOn a launched campaign the ad goes live immediately and begins consuming the\ncampaign's budget. This spends money, so the key needs ``ads:run``.","operationId":"create_campaign_ad_ad_campaigns__campaign_id__ads_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"Ad campaign ID","title":"Campaign Id"},"description":"Ad campaign ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AdCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"ads:run","x-graph8-lifecycle":"active"}},"/ad-campaigns/{campaign_id}/ads/{ad_id}":{"get":{"tags":["Ad Campaigns"],"summary":"Get Campaign Ad","description":"Fetch one ad.","operationId":"get_campaign_ad_ad_campaigns__campaign_id__ads__ad_id__get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"Ad campaign ID","title":"Campaign Id"},"description":"Ad campaign ID"},{"name":"ad_id","in":"path","required":true,"schema":{"type":"integer","description":"graph8 ad ID","title":"Ad Id"},"description":"graph8 ad ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"ads:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Ad Campaigns"],"summary":"Update Campaign Ad","description":"Edit one ad's creative.\n\nCheck ``replaced_platform_ad`` in the response: on a live campaign most\ncreative edits archive the platform ad and create a new one, restarting\npolicy review and delivery learning. The graph8 ad id and its measurement\nhistory survive that.","operationId":"update_campaign_ad_ad_campaigns__campaign_id__ads__ad_id__patch","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"Ad campaign ID","title":"Campaign Id"},"description":"Ad campaign ID"},{"name":"ad_id","in":"path","required":true,"schema":{"type":"integer","description":"graph8 ad ID","title":"Ad Id"},"description":"graph8 ad ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AdUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdUpdateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"ads:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Ad Campaigns"],"summary":"Archive Campaign Ad","description":"Permanently stop one ad.\n\nArchive, not hard-delete: Google's remove and LinkedIn's archive are both\none-way, so the ad is retained with ``status=\"archived\"`` and the spend it\nalready incurred stays attributable. Refuses on a campaign's last remaining\nad — pause or delete the campaign instead of leaving it serving nothing.","operationId":"archive_campaign_ad_ad_campaigns__campaign_id__ads__ad_id__delete","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"Ad campaign ID","title":"Campaign Id"},"description":"Ad campaign ID"},{"name":"ad_id","in":"path","required":true,"schema":{"type":"integer","description":"graph8 ad ID","title":"Ad Id"},"description":"graph8 ad ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"ads:delete","x-graph8-lifecycle":"active"}},"/ad-campaigns/{campaign_id}/ads/batch":{"post":{"tags":["Ad Campaigns"],"summary":"Create Campaign Ads Batch","description":"Add several ads at once.\n\nReturns ``status=\"partial\"`` when any individual ad failed, with per-ad\noutcomes in ``results``. Inspect those rather than treating a 200 as total\nsuccess — one creative rejected on policy does not stop its siblings.","operationId":"create_campaign_ads_batch_ad_campaigns__campaign_id__ads_batch_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"Ad campaign ID","title":"Campaign Id"},"description":"Ad campaign ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AdBatchCreateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdBatchCreateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"ads:run","x-graph8-lifecycle":"active"}},"/ad-campaigns/{campaign_id}/ads/{ad_id}/status":{"post":{"tags":["Ad Campaigns"],"summary":"Set Campaign Ad Status","description":"Pause or resume one ad, leaving its siblings and the campaign untouched.\n\nChanges what the campaign's budget is spent on, so this needs ``ads:run``.\nA LinkedIn creative still in policy review cannot be paused; that returns a\n400 with an actionable message rather than a raw platform error.","operationId":"set_campaign_ad_status_ad_campaigns__campaign_id__ads__ad_id__status_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"Ad campaign ID","title":"Campaign Id"},"description":"Ad campaign ID"},{"name":"ad_id","in":"path","required":true,"schema":{"type":"integer","description":"graph8 ad ID","title":"Ad Id"},"description":"graph8 ad ID"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AdStatusRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AdResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"ads:run","x-graph8-lifecycle":"active"}},"/crm-syncs":{"get":{"tags":["CRM Syncs"],"summary":"List Crm Syncs","description":"List configured CRM integrations for the org.","operationId":"list_crm_syncs_crm_syncs_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_CrmIntegrationResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/crm-syncs/{provider}/contacts/push":{"post":{"tags":["CRM Syncs"],"summary":"Push Contacts To Crm","description":"Push contacts to an external CRM provider.","operationId":"push_contacts_to_crm_crm_syncs__provider__contacts_push_post","parameters":[{"name":"provider","in":"path","required":true,"schema":{"$ref":"#/components/schemas/CrmProvider","description":"CRM provider"},"description":"CRM provider"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CrmPushRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPushResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/crm-syncs/{provider}/companies/push":{"post":{"tags":["CRM Syncs"],"summary":"Push Companies To Crm","description":"Push companies to an external CRM provider.","operationId":"push_companies_to_crm_crm_syncs__provider__companies_push_post","parameters":[{"name":"provider","in":"path","required":true,"schema":{"$ref":"#/components/schemas/CrmProvider","description":"CRM provider"},"description":"CRM provider"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CrmPushRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPushResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/crm-syncs/{provider}/lists/push":{"post":{"tags":["CRM Syncs"],"summary":"Push List Memberships","description":"Modify CRM list memberships (add/remove contacts).","operationId":"push_list_memberships_crm_syncs__provider__lists_push_post","parameters":[{"name":"provider","in":"path","required":true,"schema":{"$ref":"#/components/schemas/CrmProvider","description":"CRM provider"},"description":"CRM provider"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CrmPushRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/crm-syncs/{provider}/fields":{"get":{"tags":["CRM Syncs"],"summary":"Get Crm Fields","description":"Discover available fields for an entity type on a CRM provider.","operationId":"get_crm_fields_crm_syncs__provider__fields_get","parameters":[{"name":"provider","in":"path","required":true,"schema":{"$ref":"#/components/schemas/CrmProvider","description":"CRM provider"},"description":"CRM provider"},{"name":"entity_type","in":"query","required":false,"schema":{"type":"string","description":"Entity type: contacts, companies, leads, deals","default":"contacts","title":"Entity Type"},"description":"Entity type: contacts, companies, leads, deals"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmFieldsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/crm-syncs/{provider}/status":{"get":{"tags":["CRM Syncs"],"summary":"Get Crm Status","description":"Check connection health for a CRM provider.","operationId":"get_crm_status_crm_syncs__provider__status_get","parameters":[{"name":"provider","in":"path","required":true,"schema":{"$ref":"#/components/schemas/CrmProvider","description":"CRM provider"},"description":"CRM provider"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmStatusResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/connections/session-token":{"post":{"tags":["Integrations"],"summary":"Create Connection Session Token","description":"Mint a short-lived token for the hosted OAuth flow.\n\nThe token is what a browser hands to the connection provider to run the\nconsent screen; this call does not connect anything by itself. The result\nof that flow comes back to `POST /integrations/connections`.\n\nThe body is optional - omit it to take the app's default provider.","operationId":"create_connection_session_token_integrations_connections_session_token_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/SessionTokenRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ConnectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/connections":{"get":{"tags":["Integrations"],"summary":"List Connections","description":"Every CRM connection this org has.\n\nThe source of the `connection_id` every operation on\n`/integrations/crm-sync` takes.","operationId":"list_connections_integrations_connections_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ConnectionListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"},"post":{"tags":["Integrations"],"summary":"Save Connection","description":"Record a connection the OAuth flow has already established.\n\nThis does NOT perform the handshake - the hosted flow does, and this stores\nits result. `connection_id` is the id that flow returned, not one you\nchoose.","operationId":"save_connection_integrations_connections_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SaveConnectionRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ConnectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/connections/{connection_id}":{"delete":{"tags":["Integrations"],"summary":"Delete Connection","description":"Disconnect a CRM.\n\nAnything already synced STAYS - this removes the connection, not the\nrecords that came through it. Any sync configured against this connection\nstops working, so check `/integrations/crm-sync/push-enabled` first if a\ncontinuous sync is running.","operationId":"delete_connection_integrations_connections__connection_id__delete","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"Connection id.","title":"Connection Id"},"description":"Connection id."},{"name":"provider_config_key","in":"query","required":true,"schema":{"type":"string","description":"Provider config key, e.g. `hubspot` or `salesforce`. REQUIRED: the same connection id can exist under more than one provider config, so the key is what identifies which one to remove.","title":"Provider Config Key"},"description":"Provider config key, e.g. `hubspot` or `salesforce`. REQUIRED: the same connection id can exist under more than one provider config, so the key is what identifies which one to remove."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ConnectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"integrations:delete","x-graph8-lifecycle":"active"}},"/integrations/migrations/discovery":{"post":{"tags":["Integrations"],"summary":"Start Migration Discovery","description":"Look at what is in the CRM. WRITES NOTHING to graph8.\n\nCounts records, reads the field and pipeline shape, and proposes mappings.\nPoll `GET /integrations/migrations/{migration_id}` for the result, then\naccept it with `/confirm`.\n\nOrg admin, matching the app.","operationId":"start_migration_discovery_integrations_migrations_discovery_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StartDiscoveryRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ConnectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/migrations/{migration_id}":{"get":{"tags":["Integrations"],"summary":"Get Migration Status","description":"Where the migration is, and what discovery found.\n\nNOT admin-gated, matching the app: reading progress is not the privileged\npart, starting the import is.\n\nOpen-shaped, and deliberately: the payload carries a per-entity progress\nmap, the discovered fields, the proposed mappings, the pipelines and a\nWARNINGS list. A dropped warning reads as \"nothing went wrong\".","operationId":"get_migration_status_integrations_migrations__migration_id__get","parameters":[{"name":"migration_id","in":"path","required":true,"schema":{"type":"string","description":"Migration id.","title":"Migration Id"},"description":"Migration id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ConnectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/migrations/{migration_id}/confirm":{"post":{"tags":["Integrations"],"summary":"Confirm Migration","description":"Accept the discovery and START IMPORTING. Records begin landing.\n\nA migration cannot be un-run - only cancelled part-way, leaving whatever\nalready arrived. Read the status first: its `warnings` are the things\ndiscovery could not resolve on its own.\n\nAn empty body accepts the discovery as proposed, which is the point of\npreviewing it. Org admin, matching the app.","operationId":"confirm_migration_integrations_migrations__migration_id__confirm_post","parameters":[{"name":"migration_id","in":"path","required":true,"schema":{"type":"string","description":"Migration id from discovery.","title":"Migration Id"},"description":"Migration id from discovery."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ConfirmMigrationRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ConnectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/migrations/{migration_id}/cancel":{"post":{"tags":["Integrations"],"summary":"Cancel Migration","description":"Stop a running migration.\n\nRecords already imported STAY - this stops the import, it does not undo\nit. The status goes to `cancelling` rather than `cancelled`, because work\nalready in flight has to finish first.","operationId":"cancel_migration_integrations_migrations__migration_id__cancel_post","parameters":[{"name":"migration_id","in":"path","required":true,"schema":{"type":"string","description":"Migration id.","title":"Migration Id"},"description":"Migration id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ConnectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"integrations:delete","x-graph8-lifecycle":"active"}},"/integrations/migrations/delta-sync":{"post":{"tags":["Integrations"],"summary":"Start Delta Sync","description":"Import only what changed since a watermark.\n\nOMIT `since` unless you have a reason: the app picks the last successful\nwatermark, which is both what you usually want and safer than guessing.\nThe response echoes back the watermark actually used, so read it rather\nthan assuming yours was accepted.\n\nOrg admin, matching the app.","operationId":"start_delta_sync_integrations_migrations_delta_sync_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeltaSyncRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ConnectionPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/push-enabled":{"put":{"tags":["Integrations"],"summary":"Set Push Sync Enabled","description":"Turn continuous PUSH on or off for a connection.\n\n`enabled` is explicit rather than a toggle, so a retried request is\nidempotent instead of flipping the state back.","operationId":"set_push_sync_enabled_integrations_crm_sync_push_enabled_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SyncEnabledRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SyncJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/pull-enabled":{"put":{"tags":["Integrations"],"summary":"Set Pull Sync Enabled","description":"Turn continuous PULL on or off for a connection.","operationId":"set_pull_sync_enabled_integrations_crm_sync_pull_enabled_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SyncEnabledRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SyncJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/contacts/push":{"post":{"tags":["Integrations"],"summary":"Push All Contacts","description":"Push every graph8 contact into the CRM. THIS WRITES TO THEIR SYSTEM.\n\nReturns a job - the work happens in the background. Poll `/jobs/{job_id}`.\nOmit `limit` to take the app's default (10,000) rather than a number frozen\ninto this contract.","operationId":"push_all_contacts_integrations_crm_sync_contacts_push_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PushAllContactsRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SyncJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/contacts/pull":{"post":{"tags":["Integrations"],"summary":"Pull All Contacts","description":"Pull every CRM contact into graph8.\n\n`enrich_from_graph8` SPENDS ENRICHMENT CREDIT when on. Omit it to take the\napp's default rather than turning a spend on by accident.","operationId":"pull_all_contacts_integrations_crm_sync_contacts_pull_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PullAllContactsRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SyncJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/deals/push":{"post":{"tags":["Integrations"],"summary":"Push All Deals","description":"Push graph8 deals into the CRM as opportunities.","operationId":"push_all_deals_integrations_crm_sync_deals_push_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PushAllDealsRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SyncJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/deals/pull":{"post":{"tags":["Integrations"],"summary":"Pull All Deals","description":"Pull CRM opportunities into graph8 as deals.","operationId":"pull_all_deals_integrations_crm_sync_deals_pull_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PullAllDealsRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SyncJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/push":{"post":{"tags":["Integrations"],"summary":"Push Audience","description":"Push ONE audience rather than everything.\n\nThe narrow version of `/contacts/push`, and the one to reach for first: it\nbounds what lands in the customer's CRM to a list they chose.","operationId":"push_audience_integrations_crm_sync_push_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PushAudienceRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SyncJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/pull":{"post":{"tags":["Integrations"],"summary":"Pull Crm List","description":"Pull ONE CRM list rather than everything.\n\n`crm_list_id` is REQUIRED - without it there is no list to pull, and\ndefaulting to \"everything\" is the opposite of what a narrow endpoint is\nfor.","operationId":"pull_crm_list_integrations_crm_sync_pull_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PullCrmListRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SyncJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/jobs/{job_id}":{"get":{"tags":["Integrations"],"summary":"Get Sync Job","description":"How a bulk job is going.\n\nOpen-shaped: the payload carries per-provider progress detail that differs\nbetween CRMs and grows with them, so pinning it would drop whatever a\nprovider reported that we had not caught up on.","operationId":"get_sync_job_integrations_crm_sync_jobs__job_id__get","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","description":"Job id returned by a push or pull.","title":"Job Id"},"description":"Job id returned by a push or pull."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SyncJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm/objects":{"get":{"tags":["Integrations"],"summary":"List Crm Objects","description":"The CRM objects this connection can see; unsupported rows carry the reason. Read-only.\n\nAlways 200 with an explicit `status` for known states: `not_supported`, `reconnect_required` (see `missing_scopes`)\nand `access_denied`. 404 until object sync is enabled for the organisation. Owner or Admin.","operationId":"list_crm_objects_integrations_crm_objects_get","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"The CRM connection id.","title":"Connection Id"},"description":"The CRM connection id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":100,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","maximum":10000,"minimum":0,"default":0,"title":"Offset"}},{"name":"custom_only","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Custom Only"}},{"name":"q","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"description":"Search the object names.","title":"Q"},"description":"Search the object names."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmObjectCatalogPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm/objects/{object_id}/fields":{"get":{"tags":["Integrations"],"summary":"List Crm Object Fields","description":"Field names and types of one CRM object from this connection's catalog. Read-only. Owner or Admin.","operationId":"list_crm_object_fields_integrations_crm_objects__object_id__fields_get","parameters":[{"name":"object_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"The CRM object id.","title":"Object Id"},"description":"The CRM object id."},{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"The CRM connection id.","title":"Connection Id"},"description":"The CRM connection id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":100,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","maximum":10000,"minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmObjectFieldsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/object-sync/capabilities":{"get":{"tags":["Integrations"],"summary":"Get Object Sync Capability","description":"What object sync can do on this connection's CRM, and why not when it cannot. Owner or Admin.","operationId":"get_object_sync_capability_integrations_object_sync_capabilities_get","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"The CRM connection id.","title":"Connection Id"},"description":"The CRM connection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmObjectSyncPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/object-sync/setup-defaults":{"get":{"tags":["Integrations"],"summary":"Get Object Sync Setup Defaults","description":"The setup step's prefill for one CRM object, including the suggested match key. Owner or Admin.","operationId":"get_object_sync_setup_defaults_integrations_object_sync_setup_defaults_get","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"The CRM connection id.","title":"Connection Id"},"description":"The CRM connection id."},{"name":"crm_object_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"The CRM object id, e.g. `Contact` or `2-123456`.","title":"Crm Object Id"},"description":"The CRM object id, e.g. `Contact` or `2-123456`."},{"name":"object_definition_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"description":"The graph8 custom object, when chosen.","title":"Object Definition Id"},"description":"The graph8 custom object, when chosen."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmObjectSyncPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/object-sync/bindings":{"get":{"tags":["Integrations"],"summary":"List Object Sync Bindings","description":"The connection's custom-object syncs, both directions, with their last outcome (counts and codes only).","operationId":"list_object_sync_bindings_integrations_object_sync_bindings_get","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"The CRM connection id.","title":"Connection Id"},"description":"The CRM connection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmObjectSyncPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"},"post":{"tags":["Integrations"],"summary":"Create Object Sync Binding","description":"Create a one-direction sync of a CRM object into (pull) or from (push) a graph8 custom object.\n\nThe sync acts as the person who saved it on every run, so it needs a graph8 Owner or Admin who can edit records.","operationId":"create_object_sync_binding_integrations_object_sync_bindings_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CrmObjectSyncBindingCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmObjectSyncPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/object-sync/bindings/{binding_id}":{"patch":{"tags":["Integrations"],"summary":"Update Object Sync Binding","description":"Change mappings, the match key, the deletion policy or the switch. `resume` clears a pause.","operationId":"update_object_sync_binding_integrations_object_sync_bindings__binding_id__patch","parameters":[{"name":"binding_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"The binding id (UUID).","title":"Binding Id"},"description":"The binding id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CrmObjectSyncBindingUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmObjectSyncPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Integrations"],"summary":"Delete Object Sync Binding","description":"Remove a sync. graph8 records and CRM records stay as they are.","operationId":"delete_object_sync_binding_integrations_object_sync_bindings__binding_id__delete","parameters":[{"name":"binding_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"The binding id (UUID).","title":"Binding Id"},"description":"The binding id (UUID)."},{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"The CRM connection id.","title":"Connection Id"},"description":"The CRM connection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"integrations:delete","x-graph8-lifecycle":"active"}},"/integrations/object-sync/bindings/{binding_id}/run":{"post":{"tags":["Integrations"],"summary":"Run Object Sync Binding","description":"Queue one run now. THIS READS FROM OR WRITES TO THE CRM. A direction other than the binding's is a 409.","operationId":"run_object_sync_binding_integrations_object_sync_bindings__binding_id__run_post","parameters":[{"name":"binding_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"The binding id (UUID).","title":"Binding Id"},"description":"The binding id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CrmObjectSyncRunRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmObjectSyncPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/object-sync/bindings/{binding_id}/runs":{"get":{"tags":["Integrations"],"summary":"List Object Sync Runs","description":"The binding's recent runs: counts, reason codes and times, never values.","operationId":"list_object_sync_runs_integrations_object_sync_bindings__binding_id__runs_get","parameters":[{"name":"binding_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"The binding id (UUID).","title":"Binding Id"},"description":"The binding id (UUID)."},{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"The CRM connection id.","title":"Connection Id"},"description":"The CRM connection id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":20,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmObjectSyncPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/object-sync/syncs":{"put":{"tags":["Integrations"],"summary":"Put Object Sync","description":"Set one CRM object's sync to pull, push or both. Both bindings are validated once and written together.","operationId":"put_object_sync_integrations_object_sync_syncs_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CrmObjectSyncPutRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmObjectSyncPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Integrations"],"summary":"Delete Object Sync","description":"Remove both directions of one CRM object's sync in one write. Records on both sides stay.","operationId":"delete_object_sync_integrations_object_sync_syncs_delete","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"The CRM connection id.","title":"Connection Id"},"description":"The CRM connection id."},{"name":"crm_object_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"The CRM object id, e.g. `Contact` or `2-123456`.","title":"Crm Object Id"},"description":"The CRM object id, e.g. `Contact` or `2-123456`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"integrations:delete","x-graph8-lifecycle":"active"}},"/integrations/object-sync/syncs/new-object":{"post":{"tags":["Integrations"],"summary":"Create Object Sync With New Object","description":"Create a graph8 object from the CRM object (fields typed from the CRM's) and its sync, in one transaction.","operationId":"create_object_sync_with_new_object_integrations_object_sync_syncs_new_object_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CrmObjectSyncNewObjectRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmObjectSyncPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/object-sync/conflicts":{"get":{"tags":["Integrations"],"summary":"List Object Sync Conflicts","description":"Recent conflicts and CRM deletions of one CRM object's sync: record and field ids, winner and time.","operationId":"list_object_sync_conflicts_integrations_object_sync_conflicts_get","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"The CRM connection id.","title":"Connection Id"},"description":"The CRM connection id."},{"name":"crm_object_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"The CRM object id, e.g. `Contact` or `2-123456`.","title":"Crm Object Id"},"description":"The CRM object id, e.g. `Contact` or `2-123456`."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmObjectSyncPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/object-sync/conflicts/candidates":{"get":{"tags":["Integrations"],"summary":"List Object Sync Conflict Candidates","description":"The graph8 records an ambiguous CRM record could match, as the acting person may see them.\n\nA hidden field is absent and flagged; an object the person cannot read is a 403.","operationId":"list_object_sync_conflict_candidates_integrations_object_sync_conflicts_candidates_get","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"The CRM connection id.","title":"Connection Id"},"description":"The CRM connection id."},{"name":"crm_object_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"The CRM object id, e.g. `Contact` or `2-123456`.","title":"Crm Object Id"},"description":"The CRM object id, e.g. `Contact` or `2-123456`."},{"name":"crm_record_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"The ambiguous CRM record id.","title":"Crm Record Id"},"description":"The ambiguous CRM record id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmObjectSyncPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/object-sync/conflicts/resolve":{"post":{"tags":["Integrations"],"summary":"Resolve Object Sync Conflict","description":"`link` an ambiguous CRM record to one candidate or `skip` it; `archive` or `keep` the graph8 record of a CRM deletion.\n\nStored where the sync reads it, so the next run honours it. `archive` removes the graph8 record.","operationId":"resolve_object_sync_conflict_integrations_object_sync_conflicts_resolve_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CrmObjectSyncResolveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmObjectSyncPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/connections/{connection_id}/review-queue":{"get":{"tags":["Integrations"],"summary":"List Review Queue","description":"Contacts held back from CRM create because no CRM match was found, oldest first. Owner or Admin.","operationId":"list_review_queue_integrations_connections__connection_id__review_queue_get","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection id.","title":"Connection Id"},"description":"The CRM connection id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmReviewQueuePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/connections/{connection_id}/review-queue/{item_id}/resolve":{"post":{"tags":["Integrations"],"summary":"Resolve Review Item","description":"Create the contact in the CRM (THIS WRITES TO THEIR SYSTEM), link it to an existing CRM record, or skip it.","operationId":"resolve_review_item_integrations_connections__connection_id__review_queue__item_id__resolve_post","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection id.","title":"Connection Id"},"description":"The CRM connection id."},{"name":"item_id","in":"path","required":true,"schema":{"type":"string","pattern":"^[0-9a-fA-F-]{36}$","description":"The review item id (UUID).","title":"Item Id"},"description":"The review item id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CrmReviewItemResolveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmReviewQueuePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/connections/{connection_id}/field-access":{"get":{"tags":["Integrations"],"summary":"Get Connection Field Access","description":"Standard fields graph8 uses that the connected CRM user cannot access. Read-only. Owner or Admin.","operationId":"get_connection_field_access_integrations_connections__connection_id__field_access_get","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection id.","title":"Connection Id"},"description":"The CRM connection id."},{"name":"refresh","in":"query","required":false,"schema":{"type":"boolean","description":"Re-read the CRM's field description instead of the cached one.","default":false,"title":"Refresh"},"description":"Re-read the CRM's field description instead of the cached one."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmSyncRunPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/history":{"get":{"tags":["Integrations"],"summary":"Read Sync History","description":"Recent CRM sync runs: when each ran and what it processed or failed on. Owner or Admin.","operationId":"read_sync_history_integrations_crm_sync_history_get","parameters":[{"name":"connection_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"description":"Only this connection.","title":"Connection Id"},"description":"Only this connection."},{"name":"sync_type","in":"query","required":false,"schema":{"anyOf":[{"enum":["push","pull"],"type":"string"},{"type":"null"}],"title":"Sync Type"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":20,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmSyncRunPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/resync/{run_id}":{"post":{"tags":["Integrations"],"summary":"Resync From Run","description":"Re-run a prior CRM sync with the same scope. THIS WRITES TO OR READS FROM THE CRM. Returns the queued job.","operationId":"resync_from_run_integrations_crm_sync_resync__run_id__post","parameters":[{"name":"run_id","in":"path","required":true,"schema":{"type":"integer","description":"The run id from `/crm-sync/history`.","title":"Run Id"},"description":"The run id from `/crm-sync/history`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmSyncRunPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/bindings":{"get":{"tags":["Integrations"],"summary":"Read Sync Bindings","description":"The list-sync grid of one connection: each configured push or pull list with its latest run and the scheduler.","operationId":"read_sync_bindings_integrations_crm_sync_bindings_get","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"description":"The CRM connection id.","title":"Connection Id"},"description":"The CRM connection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmSyncRunPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/migrations/{migration_id}/report":{"get":{"tags":["Integrations"],"summary":"Get Migration Report","description":"Per-object report of a finished migration: expected, imported, skipped by reason, not linked, failed. Owner or Admin.","operationId":"get_migration_report_integrations_migrations__migration_id__report_get","parameters":[{"name":"migration_id","in":"path","required":true,"schema":{"type":"string","description":"The migration id.","title":"Migration Id"},"description":"The migration id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmMigrationReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/migrations/{migration_id}/report/gaps.csv":{"get":{"tags":["Integrations"],"summary":"Download Migration Gaps Csv","description":"CSV (object, source id, reason, detail) of every skipped, unlinked or missing record. Owner or Admin.","operationId":"download_migration_gaps_csv_integrations_migrations__migration_id__report_gaps_csv_get","parameters":[{"name":"migration_id","in":"path","required":true,"schema":{"type":"string","description":"The migration id.","title":"Migration Id"},"description":"The migration id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"The gap list as CSV.","content":{"text/csv":{"schema":{"type":"string"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/migrations/{migration_id}/archive":{"get":{"tags":["Integrations"],"summary":"Get Migration Archive Download","description":"Short-lived signed links to the lossless archive (gzip NDJSON per object and a manifest). Owner or Admin.","operationId":"get_migration_archive_download_integrations_migrations__migration_id__archive_get","parameters":[{"name":"migration_id","in":"path","required":true,"schema":{"type":"string","description":"The migration id.","title":"Migration Id"},"description":"The migration id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmMigrationReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/leads/push":{"post":{"tags":["Integrations"],"summary":"Push All Leads","description":"Push graph8 people into Salesforce as Leads. THIS WRITES TO THEIR SYSTEM.\n\nReturns a job - the work happens in the background. Poll\n`GET /integrations/crm-sync/jobs/{job_id}`.\n\nOver the app's population threshold the JOB is refused unless\n`large_population_confirmed` is true - the request itself is still a 202,\nand the refusal is what the job's status reports. Run\n`POST /integrations/crm-sync/leads/previews` first to learn the count you\nwould be acknowledging.","operationId":"push_all_leads_integrations_crm_sync_leads_push_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PushAllLeadsRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SyncJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/leads/pull":{"post":{"tags":["Integrations"],"summary":"Pull All Leads","description":"Pull Salesforce Leads into graph8.\n\nA body carrying only `connection_id` runs the org's SAVED `pull.leads`\nsettings rather than pulling everything. Any other field overrides those\nsettings for this run only.\n\n`enrich_from_graph8` SPENDS ENRICHMENT CREDIT when on. Omit it to take the\napp's default rather than turning a spend on by accident.","operationId":"pull_all_leads_integrations_crm_sync_leads_pull_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PullAllLeadsRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SyncJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/leads/statuses":{"get":{"tags":["Integrations"],"summary":"List Lead Statuses","description":"The org's Salesforce `Lead.Status` picklist, minus the converted ones.\n\nRead this before setting `status_qualified` / `status_unqualified` on a\npush. `Lead.Status` is an OPEN picklist: Salesforce stores whatever the API\nsends, so a typo does not fail - it creates a new status nobody meant to\nhave. Converted statuses are filtered out because setting one through a\npush would silently convert the lead.\n\nSalesforce only. Any other provider is a 400.","operationId":"list_lead_statuses_integrations_crm_sync_leads_statuses_get","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","description":"A Salesforce connection.","title":"Connection Id"},"description":"A Salesforce connection."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LeadStatusesResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/leads/push-preview":{"get":{"tags":["Integrations"],"summary":"Preview Lead Push","description":"What a lead push would do, computed NOW and returned inline.\n\nNothing is written to the CRM. The asynchronous twin,\n`POST /integrations/crm-sync/leads/previews`, queues the same work and\nreturns a job id instead - use that one for a population large enough that\nthe inline version would time out.","operationId":"preview_lead_push_integrations_crm_sync_leads_push_preview_get","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","description":"A Salesforce connection.","title":"Connection Id"},"description":"A Salesforce connection."},{"name":"source_mode","in":"query","required":false,"schema":{"enum":["all_qualified","saved_segment","segments_union","all_contacts"],"type":"string","description":"Which population to preview. `saved_segment` requires `audience_id`; `segments_union` requires `audience_ids`.","default":"all_qualified","title":"Source Mode"},"description":"Which population to preview. `saved_segment` requires `audience_id`; `segments_union` requires `audience_ids`."},{"name":"audience_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Required for `saved_segment`.","title":"Audience Id"},"description":"Required for `saved_segment`."},{"name":"audience_ids","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"integer"}},{"type":"null"}],"description":"Required for `segments_union`.","title":"Audience Ids"},"description":"Required for `segments_union`."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":10000,"minimum":1,"description":"Ceiling on rows inspected.","default":10000,"title":"Limit"},"description":"Ceiling on rows inspected."},{"name":"status_qualified","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status Qualified"}},{"name":"status_unqualified","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status Unqualified"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LeadPreviewResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/leads/previews":{"post":{"tags":["Integrations"],"summary":"Start Lead Preview","description":"Queue a readiness preview and return a job id immediately.\n\nNothing is written to the CRM. Poll\n`GET /integrations/crm-sync/jobs/{job_id}` for the result, which carries\nthe record count `large_population_confirmed` exists to acknowledge.","operationId":"start_lead_preview_integrations_crm_sync_leads_previews_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LeadPreviewRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SyncJobResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm-sync/audiences":{"post":{"tags":["Integrations"],"summary":"Get Or Create Crm Audience","description":"Get, or create, the graph8 audience a CRM import lands in.\n\nIDEMPOTENT BY TITLE. Calling twice with the same `list_name` returns the\nsame audience with `created: false` rather than making a second one, which\nis what makes it safe to call before every import. That is the difference\nfrom `POST /lists`, which always creates - and it is why this exists\nseparately rather than being folded into it.\n\nThe audience is tagged with the CRM provider and the connection it came\nfrom, so a later sync can tell CRM-imported rows from graph8-native ones.\n\n200, not 201: most calls return a list that already existed.","operationId":"get_or_create_crm_audience_integrations_crm_sync_audiences_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CrmAudienceRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmAudienceResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm/connections/{connection_id}":{"get":{"tags":["Integrations"],"summary":"Get Crm Connection","description":"What this connection is: which provider, which account, what it can do.\n\nRead this first - the provider decides which of the routes below exist.\nLeads are Salesforce-only; list membership differs per provider.","operationId":"get_crm_connection_integrations_crm_connections__connection_id__get","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm/connections/{connection_id}/status":{"get":{"tags":["Integrations"],"summary":"Get Crm Connection Status","description":"Is this connection working right now.\n\nDistinct from `GET /connections/{id}`: that describes the connection, this\none actually reaches the provider and reports whether the credentials still\nanswer.","operationId":"get_crm_connection_status_integrations_crm_connections__connection_id__status_get","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm/connections/{connection_id}/metadata":{"get":{"tags":["Integrations"],"summary":"Get Crm Connection Metadata","description":"Who connected this integration, and when.\n\nCarries no credential - the token itself is never returned by this or any\nother route on this surface.","operationId":"get_crm_connection_metadata_integrations_crm_connections__connection_id__metadata_get","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"crm_type","in":"query","required":true,"schema":{"enum":["hubspot","salesforce","pipedrive","sugarcrm","stripe","zoho-crm","freshworks","facebook-ads","linkedin-ads","google-ads","x-ads","google-search-console"],"type":"string","description":"The provider this connection belongs to. A mismatch is a 404.","title":"Crm Type"},"description":"The provider this connection belongs to. A mismatch is a 404."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm/connections/{connection_id}/contacts":{"get":{"tags":["Integrations"],"summary":"List Crm Contacts","description":"Contacts in the CRM.","operationId":"list_crm_contacts_integrations_crm_connections__connection_id__contacts_get","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":1000,"minimum":1,"description":"Records per page.","default":100,"title":"Limit"},"description":"Records per page."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Records to skip.","default":0,"title":"Offset"},"description":"Records to skip."},{"name":"updated_gte","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"description":"ISO 8601 timestamp. Only contacts modified at or after it - the parameter an incremental reader should page on rather than re-reading the whole CRM.","title":"Updated Gte"},"description":"ISO 8601 timestamp. Only contacts modified at or after it - the parameter an incremental reader should page on rather than re-reading the whole CRM."},{"name":"email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Exact-match filter.","title":"Email"},"description":"Exact-match filter."},{"name":"name","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"}},{"name":"company_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"The CRM's company id.","title":"Company Id"},"description":"The CRM's company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"},"post":{"tags":["Integrations"],"summary":"Create Crm Contact","description":"Create a contact IN THE CUSTOMER'S CRM. This writes to their system.","operationId":"create_crm_contact_integrations_crm_connections__connection_id__contacts_post","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CrmContactCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm/connections/{connection_id}/contacts/{contact_id}":{"get":{"tags":["Integrations"],"summary":"Get Crm Contact","description":"One contact, as the CRM holds it.","operationId":"get_crm_contact_integrations_crm_connections__connection_id__contacts__contact_id__get","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"contact_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM's contact id, not graph8's.","title":"Contact Id"},"description":"The CRM's contact id, not graph8's."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"},"put":{"tags":["Integrations"],"summary":"Update Crm Contact","description":"Partially update a CRM contact. Omitted fields are left alone.\n\nSending `emails: []` REPLACES the addresses with none; omitting `emails`\nleaves them. The difference is the reason this is not a PATCH-shaped\nmerge - the app's model distinguishes \"absent\" from \"empty\" and so does\nthis one.","operationId":"update_crm_contact_integrations_crm_connections__connection_id__contacts__contact_id__put","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"contact_id","in":"path","required":true,"schema":{"type":"string","title":"Contact Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CrmContactUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Integrations"],"summary":"Delete Crm Contact","description":"Delete a contact from the CUSTOMER'S CRM.\n\nWhether this is reversible is the provider's decision, not graph8's -\nHubSpot moves the record to its recycling bin, Salesforce to its recycle\nbin, and both expire. Treat it as permanent.","operationId":"delete_crm_contact_integrations_crm_connections__connection_id__contacts__contact_id__delete","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"contact_id","in":"path","required":true,"schema":{"type":"string","title":"Contact Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"integrations:delete","x-graph8-lifecycle":"active"}},"/integrations/crm/connections/{connection_id}/contacts/{contact_id}/activities":{"get":{"tags":["Integrations"],"summary":"List Crm Contact Activities","description":"This contact's timeline, read from the CRM by the CRM's own id.\n\nThe sibling `GET /integrations/crm/contact-activities` answers the same\nquestion by GRAPH8 contact id and merges in activity logged in graph8.","operationId":"list_crm_contact_activities_integrations_crm_connections__connection_id__contacts__contact_id__activities_get","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"contact_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM's contact id.","title":"Contact Id"},"description":"The CRM's contact id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":50,"title":"Limit"}},{"name":"activity_types","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated: `calls,emails,notes,meetings,tasks`.","title":"Activity Types"},"description":"Comma-separated: `calls,emails,notes,meetings,tasks`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm/connections/{connection_id}/batch/contacts":{"post":{"tags":["Integrations"],"summary":"Batch Create Crm Contacts","description":"Create many contacts in one provider round trip.\n\nPARTIAL SUCCESS IS POSSIBLE. The response carries per-record outcomes;\na 201 does not mean every record landed. Read them before retrying, or a\nretry duplicates the ones that succeeded.","operationId":"batch_create_crm_contacts_integrations_crm_connections__connection_id__batch_contacts_post","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BatchContactsRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"},"put":{"tags":["Integrations"],"summary":"Batch Update Crm Contacts","description":"Update many contacts in one provider round trip.\n\nEach entry needs `crm_id` - on this path it identifies the record to\nupdate, and an entry without one cannot be matched. Partial success is\npossible here too.","operationId":"batch_update_crm_contacts_integrations_crm_connections__connection_id__batch_contacts_put","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BatchContactsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm/connections/{connection_id}/batch/contacts/lookup-by-email":{"post":{"tags":["Integrations"],"summary":"Lookup Crm Contacts By Email","description":"Find existing CRM contacts by email address. READS ONLY.\n\nPOST because a list of emails is a body, not because it changes anything -\nand it is tiered `read` for that reason, so a key granted \"read my CRM\" can\ncall it. This is the de-duplication check to run BEFORE a create.","operationId":"lookup_crm_contacts_by_email_integrations_crm_connections__connection_id__batch_contacts_lookup_by_email_post","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BatchGetByEmailRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm/connections/{connection_id}/companies":{"get":{"tags":["Integrations"],"summary":"List Crm Companies","description":"Companies (accounts) in the CRM.","operationId":"list_crm_companies_integrations_crm_connections__connection_id__companies_get","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":1000,"minimum":1,"description":"Records per page.","default":100,"title":"Limit"},"description":"Records per page."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Records to skip.","default":0,"title":"Offset"},"description":"Records to skip."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"},"post":{"tags":["Integrations"],"summary":"Create Crm Company","description":"Create a company IN THE CUSTOMER'S CRM.","operationId":"create_crm_company_integrations_crm_connections__connection_id__companies_post","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CrmCompanyCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm/connections/{connection_id}/companies/{company_id}":{"get":{"tags":["Integrations"],"summary":"Get Crm Company","description":"One company, as the CRM holds it.","operationId":"get_crm_company_integrations_crm_connections__connection_id__companies__company_id__get","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM's company id, not graph8's.","title":"Company Id"},"description":"The CRM's company id, not graph8's."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"},"put":{"tags":["Integrations"],"summary":"Update Crm Company","description":"Partially update a CRM company. Omitted fields are left alone.","operationId":"update_crm_company_integrations_crm_connections__connection_id__companies__company_id__put","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"company_id","in":"path","required":true,"schema":{"type":"string","title":"Company Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CrmCompanyUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm/connections/{connection_id}/deals":{"get":{"tags":["Integrations"],"summary":"List Crm Deals","description":"Deals (opportunities) in the CRM.\n\nNot graph8 deals. `GET /deals` is those, and the two have different ids.","operationId":"list_crm_deals_integrations_crm_connections__connection_id__deals_get","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":1000,"minimum":1,"description":"Records per page.","default":100,"title":"Limit"},"description":"Records per page."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Records to skip.","default":0,"title":"Offset"},"description":"Records to skip."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"},"post":{"tags":["Integrations"],"summary":"Create Crm Deal","description":"Create a deal IN THE CUSTOMER'S CRM.","operationId":"create_crm_deal_integrations_crm_connections__connection_id__deals_post","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CrmDealCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm/connections/{connection_id}/deals/{deal_id}":{"get":{"tags":["Integrations"],"summary":"Get Crm Deal","description":"One deal, as the CRM holds it.","operationId":"get_crm_deal_integrations_crm_connections__connection_id__deals__deal_id__get","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM's deal id, not graph8's.","title":"Deal Id"},"description":"The CRM's deal id, not graph8's."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"},"put":{"tags":["Integrations"],"summary":"Update Crm Deal","description":"Partially update a CRM deal. Omitted fields are left alone.\n\nMoving `stage` is what closes a deal in most CRMs, and it can fire that\nprovider's own workflows and notifications.","operationId":"update_crm_deal_integrations_crm_connections__connection_id__deals__deal_id__put","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","title":"Deal Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CrmDealUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm/connections/{connection_id}/leads":{"get":{"tags":["Integrations"],"summary":"List Crm Leads","description":"Leads in the CRM. Salesforce only.","operationId":"list_crm_leads_integrations_crm_connections__connection_id__leads_get","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":1000,"minimum":1,"description":"Records per page.","default":100,"title":"Limit"},"description":"Records per page."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Records to skip.","default":0,"title":"Offset"},"description":"Records to skip."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"},"post":{"tags":["Integrations"],"summary":"Create Crm Lead","description":"Create a Lead IN THE CUSTOMER'S SALESFORCE.\n\n`last_name` and `company` are required by Salesforce itself. `status` is an\nOPEN picklist - read the valid values from\n`GET /integrations/crm-sync/leads/statuses` first, because an invented one\nis stored rather than refused.","operationId":"create_crm_lead_integrations_crm_connections__connection_id__leads_post","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LeadCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm/connections/{connection_id}/leads/{lead_id}":{"get":{"tags":["Integrations"],"summary":"Get Crm Lead","description":"One lead, as the CRM holds it.","operationId":"get_crm_lead_integrations_crm_connections__connection_id__leads__lead_id__get","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"lead_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM's lead id.","title":"Lead Id"},"description":"The CRM's lead id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"},"put":{"tags":["Integrations"],"summary":"Update Crm Lead","description":"Partially update a Salesforce Lead. Omitted fields are left alone.","operationId":"update_crm_lead_integrations_crm_connections__connection_id__leads__lead_id__put","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"lead_id","in":"path","required":true,"schema":{"type":"string","title":"Lead Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LeadUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm/users":{"get":{"tags":["Integrations"],"summary":"List Crm Users","description":"The CRM's own users - the ids that `user_id` on a create or update means.","operationId":"list_crm_users_integrations_crm_users_get","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","description":"The CRM connection to act through.","title":"Connection Id"},"description":"The CRM connection to act through."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm/users/by-email":{"get":{"tags":["Integrations"],"summary":"Find Crm User By Email","description":"Resolve one CRM user by email, for setting record ownership.\n\nReturns a LIST, not one user: a CRM can hold more than one user against an\naddress, and picking one here would hide that from the caller.","operationId":"find_crm_user_by_email_integrations_crm_users_by_email_get","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","title":"Connection Id"}},{"name":"email","in":"query","required":true,"schema":{"type":"string","description":"The user's address in the CRM.","title":"Email"},"description":"The user's address in the CRM."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm/meetings":{"get":{"tags":["Integrations"],"summary":"List Crm Meetings","description":"Meetings on the CRM's calendar object.\n\nNot graph8 appointments - `/appointments/*` is those.","operationId":"list_crm_meetings_integrations_crm_meetings_get","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","title":"Connection Id"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":1000,"minimum":1,"description":"Records per page.","default":100,"title":"Limit"},"description":"Records per page."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Records to skip.","default":0,"title":"Offset"},"description":"Records to skip."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"},"post":{"tags":["Integrations"],"summary":"Create Crm Meeting","description":"Create a meeting on the CRM's calendar and associate it with records.\n\nThis does not send an invitation - it records the meeting on the CRM\nobject. `/appointments/*` is the surface that books with a person.","operationId":"create_crm_meeting_integrations_crm_meetings_post","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","title":"Connection Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateMeetingRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm/meetings/{event_id}":{"patch":{"tags":["Integrations"],"summary":"Update Crm Meeting","description":"Partially update a CRM meeting.","operationId":"update_crm_meeting_integrations_crm_meetings__event_id__patch","parameters":[{"name":"event_id","in":"path","required":true,"schema":{"type":"string","description":"The CRM's event id.","title":"Event Id"},"description":"The CRM's event id."},{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","title":"Connection Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateMeetingRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm/activities":{"get":{"tags":["Integrations"],"summary":"List Crm Activities","description":"Activities across the whole CRM, unscoped to a record.","operationId":"list_crm_activities_integrations_crm_activities_get","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","title":"Connection Id"}},{"name":"type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"One activity type, e.g. `call`.","title":"Type"},"description":"One activity type, e.g. `call`."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":1000,"minimum":1,"description":"Records per page.","default":100,"title":"Limit"},"description":"Records per page."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Records to skip.","default":0,"title":"Offset"},"description":"Records to skip."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm/contact-activities":{"get":{"tags":["Integrations"],"summary":"List Contact Activities By Graph8 Id","description":"One contact's merged timeline, by GRAPH8 contact id.\n\nRow visibility follows the key's own contact scope - the same filter the\nbrowser applies, resolved from the key rather than from a session.","operationId":"list_contact_activities_by_graph8_id_integrations_crm_contact_activities_get","parameters":[{"name":"contact_id","in":"query","required":true,"schema":{"type":"integer","description":"graph8 `mashup_contacts.id`.","title":"Contact Id"},"description":"graph8 `mashup_contacts.id`."},{"name":"connection_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Auto-discovered from the org's connections when omitted.","title":"Connection Id"},"description":"Auto-discovered from the org's connections when omitted."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":50,"title":"Limit"}},{"name":"activity_types","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated: `calls,emails,notes,meetings,tasks`.","title":"Activity Types"},"description":"Comma-separated: `calls,emails,notes,meetings,tasks`."},{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"`manual`, `crm` (any provider), or a provider name. Omit for everything - which is the point of this route: one timeline whether the activity was logged in graph8 or in the CRM.","title":"Source"},"description":"`manual`, `crm` (any provider), or a provider name. Omit for everything - which is the point of this route: one timeline whether the activity was logged in graph8 or in the CRM."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm/company-activities":{"get":{"tags":["Integrations"],"summary":"List Company Activities By Graph8 Id","description":"One company's merged timeline, by GRAPH8 company id.\n\nRow visibility follows the key's own company scope.","operationId":"list_company_activities_by_graph8_id_integrations_crm_company_activities_get","parameters":[{"name":"company_id","in":"query","required":true,"schema":{"type":"integer","description":"graph8 `mashup_companies.id`.","title":"Company Id"},"description":"graph8 `mashup_companies.id`."},{"name":"activity_types","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated activity types.","title":"Activity Types"},"description":"Comma-separated activity types."},{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"`manual` or `crm`.","title":"Source"},"description":"`manual` or `crm`."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm/fields":{"get":{"tags":["Integrations"],"summary":"Discover Crm Fields","description":"The CRM's own fields for one object, including its custom ones.\n\nThis is where a valid `custom_fields[].field_name` comes from. The provider\nrejects a name it does not have, so read this before writing one.","operationId":"discover_crm_fields_integrations_crm_fields_get","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","title":"Connection Id"}},{"name":"entity_type","in":"query","required":false,"schema":{"enum":["contacts","companies","deals","leads","meetings","tasks","activities"],"type":"string","description":"Which CRM object to describe. `meetings`/`tasks` are Salesforce's Event/Task and `activities` is Pipedrive's; other providers fall back to contacts for an object they do not model.","default":"contacts","title":"Entity Type"},"description":"Which CRM object to describe. `meetings`/`tasks` are Salesforce's Event/Task and `activities` is Pipedrive's; other providers fall back to contacts for an object they do not model."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm/fields/mappable":{"get":{"tags":["Integrations"],"summary":"List Mappable Graph8 Fields","description":"The GRAPH8-side fields a CRM field can be mapped onto.\n\nThe other half of `GET /integrations/crm/fields`: that one describes the\ncustomer's CRM, this one describes graph8. A field mapping is a pair drawn\nfrom the two, so both have to be readable for one to be buildable.\n\n`activities` is accepted here and not by `/fields` - it is a graph8-side\nobject that has no single CRM counterpart.","operationId":"list_mappable_graph8_fields_integrations_crm_fields_mappable_get","parameters":[{"name":"object_type","in":"query","required":false,"schema":{"enum":["contacts","companies","deals","leads","activities"],"type":"string","description":"Which graph8 object.","default":"contacts","title":"Object Type"},"description":"Which graph8 object."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/crm/lists":{"get":{"tags":["Integrations"],"summary":"List Crm Lists","description":"Lists in the CRM.\n\nPublished as GET although the app spells it POST: every one of its\nparameters is a QUERY parameter and it reads. A POST that takes no body is\na read wearing the wrong verb, and publishing it that way would put this\nbehind a write grant for no reason.","operationId":"list_crm_lists_integrations_crm_lists_get","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","title":"Connection Id"}},{"name":"query","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by list name.","title":"Query"},"description":"Filter by list name."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":250,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"entity_type","in":"query","required":false,"schema":{"enum":["contacts","companies","deals","leads"],"type":"string","description":"Which object the list holds.","default":"contacts","title":"Entity Type"},"description":"Which object the list holds."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"},"post":{"tags":["Integrations"],"summary":"Get Or Create Crm List","description":"Get, or create, a list IN THE CUSTOMER'S CRM, matched by name.\n\nIDEMPOTENT: calling twice with the same name returns the existing list\nrather than making a second one, which is what makes it safe to call before\nevery membership change. 200, not 201, because most calls return a list\nthat already existed.\n\nThe app takes these three as query parameters on a POST; they are a body\nhere, because a POST carrying its arguments in the query string is not a\nshape to put in a public contract.","operationId":"get_or_create_crm_list_integrations_crm_lists_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/GetOrCreateCrmListRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/crm/lists/memberships":{"post":{"tags":["Integrations"],"summary":"Modify Crm List Memberships","description":"Add and remove contacts from ONE CRM list, in a single call.\n\nBoth directions are applied in the same request, so this is not two calls\npretending to be one - and repeating the same body is idempotent on the\nprovider side. Membership drives who receives the customer's CRM-side\nmarketing, which is why it is admin-gated.","operationId":"modify_crm_list_memberships_integrations_crm_lists_memberships_post","parameters":[{"name":"connection_id","in":"query","required":true,"schema":{"type":"string","title":"Connection Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ModifyListMembershipsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CrmPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/connection":{"get":{"tags":["LinkedIn Outreach"],"summary":"Get Outreach Connection","description":"Whether LinkedIn outreach is connected and its session healthy. Reports state, never credentials.","operationId":"get_outreach_connection_integrations_linkedin_outreach_connection_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachConnectionStatus_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/connection/reconnect":{"post":{"tags":["LinkedIn Outreach"],"summary":"Reconnect Outreach","description":"Refresh an expired session using the credentials already stored. Takes no credentials.\n\n`requires_login: true` means the stored ones no longer work and a person must sign in again in the app.","operationId":"reconnect_outreach_integrations_linkedin_outreach_connection_reconnect_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachReconnectResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/workspaces":{"get":{"tags":["LinkedIn Outreach"],"summary":"List Outreach Workspaces","description":"Workspaces available to select. Empty once one is selected; `current_workspace_id` then names it.","operationId":"list_outreach_workspaces_integrations_linkedin_outreach_workspaces_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachWorkspaces_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/workspaces/active":{"get":{"tags":["LinkedIn Outreach"],"summary":"Get Active Outreach Workspace","description":"The workspace this org sends from, if one is selected.","operationId":"get_active_outreach_workspace_integrations_linkedin_outreach_workspaces_active_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachWorkspaceState_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"},"put":{"tags":["LinkedIn Outreach"],"summary":"Select Active Outreach Workspace","description":"Select the workspace this org sends from. ONE-TIME: a second call is a 409.\n\nEvery sender account, list and campaign on this surface is read from the selected workspace.","operationId":"select_active_outreach_workspace_integrations_linkedin_outreach_workspaces_active_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OutreachWorkspaceSelectRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachWorkspaceSelected_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/workspaces/sync":{"post":{"tags":["LinkedIn Outreach"],"summary":"Sync Outreach Workspace","description":"Confirm the workspace configuration. Reads only: `success: false` means none is selected yet.","operationId":"sync_outreach_workspace_integrations_linkedin_outreach_workspaces_sync_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachWorkspaceState_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/accounts":{"get":{"tags":["LinkedIn Outreach"],"summary":"List Outreach Sender Accounts","description":"LinkedIn accounts that send outreach in the selected workspace.","operationId":"list_outreach_sender_accounts_integrations_linkedin_outreach_accounts_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachSenderAccounts_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/templates":{"get":{"tags":["LinkedIn Outreach"],"summary":"List Outreach Templates","description":"Pre-built campaign sequence templates.","operationId":"list_outreach_templates_integrations_linkedin_outreach_templates_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachTemplates_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/lists":{"get":{"tags":["LinkedIn Outreach"],"summary":"List Outreach Lists","description":"Lead lists on the outreach platform (not graph8 lists - those are `/lists`).","operationId":"list_outreach_lists_integrations_linkedin_outreach_lists_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"ZERO-indexed, passed through to the platform.","default":0,"title":"Page"},"description":"ZERO-indexed, passed through to the platform."},{"name":"search","in":"query","required":false,"schema":{"type":"string","description":"Substring match on the list name.","default":"","title":"Search"},"description":"Substring match on the list name."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachLists_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"},"post":{"tags":["LinkedIn Outreach"],"summary":"Create Outreach List","description":"Create an empty lead list on the outreach platform.","operationId":"create_outreach_list_integrations_linkedin_outreach_lists_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OutreachListCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachListCreated_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/lists/{list_id}/leads":{"post":{"tags":["LinkedIn Outreach"],"summary":"Add Outreach List Leads","description":"Add people to a lead list. REAL OUTREACH: any campaign running on this list starts contacting them.","operationId":"add_outreach_list_leads_integrations_linkedin_outreach_lists__list_id__leads_post","parameters":[{"name":"list_id","in":"path","required":true,"schema":{"type":"integer","description":"The outreach lead list's id.","title":"List Id"},"description":"The outreach lead list's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OutreachAddLeadsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachLeadsAdded_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/campaigns":{"get":{"tags":["LinkedIn Outreach"],"summary":"List Outreach Campaigns","description":"Outreach campaigns in the selected workspace.","operationId":"list_outreach_campaigns_integrations_linkedin_outreach_campaigns_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"ZERO-indexed, passed through to the platform.","default":0,"title":"Page"},"description":"ZERO-indexed, passed through to the platform."},{"name":"keyword","in":"query","required":false,"schema":{"type":"string","description":"Substring match on the campaign name.","default":"","title":"Keyword"},"description":"Substring match on the campaign name."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachCampaigns_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/campaigns/{campaign_id}/stats":{"get":{"tags":["LinkedIn Outreach"],"summary":"Get Outreach Campaign Stats","description":"Profile views, connection requests, messages, replies and their rates for one campaign.","operationId":"get_outreach_campaign_stats_integrations_linkedin_outreach_campaigns__campaign_id__stats_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"The outreach campaign's id.","title":"Campaign Id"},"description":"The outreach campaign's id."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"YYYY-MM-DD. Omit both dates for all time.","title":"Start Date"},"description":"YYYY-MM-DD. Omit both dates for all time."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"YYYY-MM-DD.","title":"End Date"},"description":"YYYY-MM-DD."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachCampaignStats_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/campaigns/{campaign_id}/progress":{"get":{"tags":["LinkedIn Outreach"],"summary":"Get Outreach Campaign Progress","description":"How far through its leads a campaign is: pending, in progress, finished, failed, stopped, excluded.","operationId":"get_outreach_campaign_progress_integrations_linkedin_outreach_campaigns__campaign_id__progress_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"The outreach campaign's id.","title":"Campaign Id"},"description":"The outreach campaign's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachCampaignProgress_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/campaigns/{campaign_id}/pause":{"post":{"tags":["LinkedIn Outreach"],"summary":"Pause Outreach Campaign","description":"Stop a running campaign sending, on the platform itself. Reversible with `/resume`.","operationId":"pause_outreach_campaign_integrations_linkedin_outreach_campaigns__campaign_id__pause_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"The outreach campaign's id.","title":"Campaign Id"},"description":"The outreach campaign's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachCampaignActionResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/campaigns/{campaign_id}/resume":{"post":{"tags":["LinkedIn Outreach"],"summary":"Resume Outreach Campaign","description":"Resume a paused campaign. OUTREACH RESTARTS IMMEDIATELY.","operationId":"resume_outreach_campaign_integrations_linkedin_outreach_campaigns__campaign_id__resume_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"The outreach campaign's id.","title":"Campaign Id"},"description":"The outreach campaign's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachCampaignActionResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/campaigns/{campaign_id}/leads/search":{"post":{"tags":["LinkedIn Outreach"],"summary":"Search Outreach Campaign Leads","description":"Who is in a campaign and what has happened to each of them. READS ONLY - POST because paging is a body.","operationId":"search_outreach_campaign_leads_integrations_linkedin_outreach_campaigns__campaign_id__leads_search_post","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"integer","description":"The outreach campaign's id.","title":"Campaign Id"},"description":"The outreach campaign's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OutreachCampaignLeadsQuery"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachCampaignLeads_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/sequences/{sequence_id}/mapping":{"get":{"tags":["LinkedIn Outreach"],"summary":"Get Outreach Sequence Mapping","description":"The outreach campaign and lead list a sequence runs through. 404 when it has none.","operationId":"get_outreach_sequence_mapping_integrations_linkedin_outreach_sequences__sequence_id__mapping_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"The graph8 sequence's id.","title":"Sequence Id"},"description":"The graph8 sequence's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachSequenceMapping_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/sequences/{sequence_id}/step-campaigns":{"get":{"tags":["LinkedIn Outreach"],"summary":"List Outreach Sequence Step Campaigns","description":"The campaign behind each LinkedIn step of a sequence, keyed by step id.","operationId":"list_outreach_sequence_step_campaigns_integrations_linkedin_outreach_sequences__sequence_id__step_campaigns_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"The graph8 sequence's id.","title":"Sequence Id"},"description":"The graph8 sequence's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachStepCampaigns_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/linkedin-outreach/sequences/{sequence_id}/progress":{"get":{"tags":["LinkedIn Outreach"],"summary":"Get Outreach Sequence Progress","description":"Progress of the campaign a sequence runs through. 404 when the sequence has none.","operationId":"get_outreach_sequence_progress_integrations_linkedin_outreach_sequences__sequence_id__progress_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"The graph8 sequence's id.","title":"Sequence Id"},"description":"The graph8 sequence's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OutreachCampaignProgress_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/linkedin/accounts":{"get":{"tags":["LinkedIn"],"summary":"List Linkedin Sender Accounts","description":"Sender accounts with today's invite and message usage against their caps, and the queue waiting.\n\nEmpty (not an error) when LinkedIn sending is not enabled for the org or no account has been synced.","operationId":"list_linkedin_sender_accounts_linkedin_accounts_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LinkedInAccountPlans_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/linkedin/accounts/{account_id}/schedule":{"get":{"tags":["LinkedIn"],"summary":"Get Linkedin Account Schedule","description":"The account's send window. `schedule: null` means none is set and the default window applies.","operationId":"get_linkedin_account_schedule_linkedin_accounts__account_id__schedule_get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"`account_id` from `GET /linkedin/accounts`.","title":"Account Id"},"description":"`account_id` from `GET /linkedin/accounts`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LinkedInScheduleState_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"},"put":{"tags":["LinkedIn"],"summary":"Set Linkedin Account Schedule","description":"Set or replace the account's send window.\n\nWritten to the sending provider first, then stored; a provider failure is a\n502 and nothing changes. A timezone change takes effect at the account's\nnext local midnight - `effective_from` says exactly when.","operationId":"set_linkedin_account_schedule_linkedin_accounts__account_id__schedule_put","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"`account_id` from `GET /linkedin/accounts`.","title":"Account Id"},"description":"`account_id` from `GET /linkedin/accounts`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LinkedInScheduleRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LinkedInSchedule_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/linkedin/connection":{"get":{"tags":["LinkedIn"],"summary":"Get Linkedin Connection Status","description":"Whether LinkedIn sending is connected, how many accounts are synced, and whether any needs attention.\n\nReports that a credential exists - never the credential.","operationId":"get_linkedin_connection_status_linkedin_connection_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LinkedInConnectionStatus_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/linkedin/accounts/sync":{"post":{"tags":["LinkedIn"],"summary":"Sync Linkedin Sender Accounts","description":"Re-read the org's LinkedIn accounts from the sending provider.\n\nAccounts the provider no longer returns are marked removed and stop sending.","operationId":"sync_linkedin_sender_accounts_linkedin_accounts_sync_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LinkedInAccountSyncResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/linkedin/approvals":{"get":{"tags":["LinkedIn"],"summary":"List Linkedin Pending Approvals","description":"LinkedIn messages and noted invites waiting for the seat owner's approval, oldest first.\n\nLists only what the caller may decide (a seat they own, or every seat for an admin). `total_count` spans all pages.","operationId":"list_linkedin_pending_approvals_linkedin_approvals_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LinkedInApprovalPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/linkedin/approvals/{approval_id}/approve":{"post":{"tags":["LinkedIn"],"summary":"Approve Linkedin Message","description":"Approve a pending LinkedIn message or invite, optionally with edited text. IT IS THEN SENT.\n\nOnly the seat's owner or an org admin may approve; anyone else gets 403, and an unknown or already decided\napproval is 404 or 409. A key reaches an approval only inside its own organisation.","operationId":"approve_linkedin_message_linkedin_approvals__approval_id__approve_post","parameters":[{"name":"approval_id","in":"path","required":true,"schema":{"type":"string","description":"Approval id (the LinkedIn action queue id).","title":"Approval Id"},"description":"Approval id (the LinkedIn action queue id)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/LinkedInApproveRequest"},{"type":"null"}],"title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LinkedInApprovalPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/linkedin/approvals/{approval_id}/reject":{"post":{"tags":["LinkedIn"],"summary":"Reject Linkedin Message","description":"Reject a pending approval: nothing is sent, the step is skipped and the sequence continues.\n\n`sequence_outcome` reports what the contact's sequence did next. Same permission as approving.","operationId":"reject_linkedin_message_linkedin_approvals__approval_id__reject_post","parameters":[{"name":"approval_id","in":"path","required":true,"schema":{"type":"string","description":"Approval id (the LinkedIn action queue id).","title":"Approval Id"},"description":"Approval id (the LinkedIn action queue id)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LinkedInApprovalPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/linkedin/accounts/{account_id}/settings":{"get":{"tags":["LinkedIn"],"summary":"Get Linkedin Seat Settings","description":"A seat's approval switches and whether the caller may change them (`can_edit`). 404 for another org's seat.","operationId":"get_linkedin_seat_settings_linkedin_accounts__account_id__settings_get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"LinkedIn seat (account) id, `lia_...`.","title":"Account Id"},"description":"LinkedIn seat (account) id, `lia_...`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LinkedInApprovalPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"},"patch":{"tags":["LinkedIn"],"summary":"Update Linkedin Seat Settings","description":"Change a seat's `require_message_approval` and/or `shared_with_team`. Send at least one.\n\nSWITCHING APPROVAL OFF RELEASES EVERY HELD MESSAGE TO SEND AS DRAFTED (`released_count`); there is no expiry, so\nthe queue goes out. Only the seat's owner or an org admin may change it. `shared_with_team` lets teammates publish\nthrough the seat.","operationId":"update_linkedin_seat_settings_linkedin_accounts__account_id__settings_patch","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"LinkedIn seat (account) id, `lia_...`.","title":"Account Id"},"description":"LinkedIn seat (account) id, `lia_...`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LinkedInSeatSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LinkedInApprovalPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/integrations/sugarcrm/connect":{"post":{"tags":["Integrations"],"summary":"Connect Sugarcrm","description":"Connect SugarCRM. REACHES YOUR SUGARCRM to authenticate first.\n\n409 when a SugarCRM connection already exists - rotate its credentials\nwith `/sugarcrm/reconnect` instead. 400 for an instance URL that does not\nresolve to a public host, 401 when SugarCRM rejects the credentials.","operationId":"connect_sugarcrm_integrations_sugarcrm_connect_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SugarCrmConnectRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntegrationOpPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/sugarcrm/validate":{"post":{"tags":["Integrations"],"summary":"Validate Sugarcrm","description":"Check the stored SugarCRM connection still works, and as whom.\n\nReads only. `valid: false` means SugarCRM refused the stored credentials;\n404 means there is no SugarCRM connection.","operationId":"validate_sugarcrm_integrations_sugarcrm_validate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntegrationOpPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/sugarcrm/reconnect":{"post":{"tags":["Integrations"],"summary":"Reconnect Sugarcrm","description":"Replace the stored SugarCRM credentials (or connect, if none exist).\n\nAuthenticates with the NEW credentials before saving them, so a typo\nleaves the working connection in place.","operationId":"reconnect_sugarcrm_integrations_sugarcrm_reconnect_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SugarCrmConnectRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntegrationOpPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/integrations/sugarcrm":{"delete":{"tags":["Integrations"],"summary":"Disconnect Sugarcrm","description":"Disconnect SugarCRM: drop its tokens and remove the connection.\n\nRecords already synced into graph8 stay. Sync to and from SugarCRM stops.","operationId":"disconnect_sugarcrm_integrations_sugarcrm_delete","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntegrationOpPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"integrations:delete","x-graph8-lifecycle":"active"}},"/integrations/connections/{connection_id}/last-migration":{"get":{"tags":["Integrations"],"summary":"Get Last Completed Migration","description":"The most recent COMPLETED migration from this connection, or\n`migration: null` if there has never been one.\n\nA later cancelled or failed run does not hide it: once a connection has\nbeen migrated successfully, a delta sync stays available.","operationId":"get_last_completed_migration_integrations_connections__connection_id__last_migration_get","parameters":[{"name":"connection_id","in":"path","required":true,"schema":{"type":"string","description":"CRM connection id.","title":"Connection Id"},"description":"CRM connection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntegrationOpPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/intent/keywords/preview":{"post":{"tags":["Signals"],"summary":"Preview Keyword Urls","description":"Estimate how many URLs a keyword and filters would match, WITHOUT creating it.\n\nReads pages already crawled; starts no crawl and creates nothing. Returns\n`estimated_url_count`, `baseline_url_count` and a `filter_impact` breakdown.","operationId":"preview_keyword_urls_intent_keywords_preview_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PreviewKeywordUrlsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/intent/keywords/auto-seed-proposals":{"post":{"tags":["Signals"],"summary":"Propose Hiring Keywords","description":"Propose hiring listeners from the org's own personas and ICP.\n\nPROPOSALS, not keywords: nothing is created - add the ones you want with\n`POST /intent/keywords/add`. Generating them runs a model, so the org must\nhave credit (402 otherwise). Falls back to a starter set when the org has no\ncontext documents yet.","operationId":"propose_hiring_keywords_intent_keywords_auto_seed_proposals_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AutoSeedProposalsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/intent/keywords/{keyword_id}":{"patch":{"tags":["Signals"],"summary":"Update Hiring Keyword","description":"Edit a HIRING listener in place: its name, filters or watchlist scope.\n\nOnly `jobs` and `job_changes` listeners are editable here; any other keyword\nis a 404. `search_filters` is a FULL REPLACEMENT.","operationId":"update_hiring_keyword_intent_keywords__keyword_id__patch","parameters":[{"name":"keyword_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"The keyword's id.","title":"Keyword Id"},"description":"The keyword's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateKeywordRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Intent"],"summary":"Keywords Delete","description":"Soft-delete a compete-tracking keyword row.","operationId":"keywords_delete_intent_keywords__keyword_id__delete","parameters":[{"name":"keyword_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Keyword row UUID.","title":"Keyword Id"},"description":"Keyword row UUID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"intent:delete","x-graph8-lifecycle":"active"}},"/intent/keyword-urls/{url_id}":{"delete":{"tags":["Signals"],"summary":"Delete Keyword Url","description":"Remove one URL from a keyword's matched set (soft delete).","operationId":"delete_keyword_url_intent_keyword_urls__url_id__delete","parameters":[{"name":"url_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"The keyword URL's id.","title":"Url Id"},"description":"The keyword URL's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"intent:delete","x-graph8-lifecycle":"active"}},"/intent/keywords/{keyword_id}/sync-config":{"get":{"tags":["Signals"],"summary":"Get Keyword Sync Config","description":"Which list this keyword feeds, and whether on a schedule. Defaults when never configured.","operationId":"get_keyword_sync_config_intent_keywords__keyword_id__sync_config_get","parameters":[{"name":"keyword_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"The keyword's id.","title":"Keyword Id"},"description":"The keyword's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Signals"],"summary":"Save Keyword Sync Config","description":"Wire this keyword to a list (upsert).\n\n`auto_sync_enabled: true` is the consequential field: from then on the\nkeyword's matches are pushed into `list_id` on a schedule, and anything\ndownstream of that list runs on the people it found.","operationId":"save_keyword_sync_config_intent_keywords__keyword_id__sync_config_patch","parameters":[{"name":"keyword_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"The keyword's id.","title":"Keyword Id"},"description":"The keyword's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/KeywordSyncConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/intent/keywords/{keyword_id}/sync":{"post":{"tags":["Signals"],"summary":"Trigger Keyword Sync","description":"Queue an immediate sync of this keyword's matches into its configured list.","operationId":"trigger_keyword_sync_intent_keywords__keyword_id__sync_post","parameters":[{"name":"keyword_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"The keyword's id.","title":"Keyword Id"},"description":"The keyword's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/intent/keywords/{keyword_id}/job-resolution":{"post":{"tags":["Signals"],"summary":"Resolve Jobs For Keyword","description":"Run the jobs resolver for this keyword NOW, instead of waiting for the hourly run.\n\nSynchronous: returns the decision makers and recruiters emitted and the\nwall time taken.","operationId":"resolve_jobs_for_keyword_intent_keywords__keyword_id__job_resolution_post","parameters":[{"name":"keyword_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"The keyword's id.","title":"Keyword Id"},"description":"The keyword's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"},"get":{"tags":["Signals"],"summary":"Get Job Resolution Status","description":"When the resolver last ran for this keyword, and what it emitted. Empty if it never has.","operationId":"get_job_resolution_status_intent_keywords__keyword_id__job_resolution_get","parameters":[{"name":"keyword_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"The keyword's id.","title":"Keyword Id"},"description":"The keyword's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/intent/abm/companies":{"get":{"tags":["Signals"],"summary":"List Abm Companies","description":"Accounts showing intent, one scored row per company, with buying-committee coverage.","operationId":"list_abm_companies_intent_abm_companies_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Look-back window in days.","default":30,"title":"Days"},"description":"Look-back window in days."},{"name":"keyword_ids","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated keyword ids to restrict to.","title":"Keyword Ids"},"description":"Comma-separated keyword ids to restrict to."},{"name":"icp_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"description":"Score against this ICP.","title":"Icp Id"},"description":"Score against this ICP."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":50,"title":"Limit"}},{"name":"agFilterModel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Grid filter model as JSON, passed through unchanged.","title":"Agfiltermodel"},"description":"Grid filter model as JSON, passed through unchanged."},{"name":"agSortModel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Grid sort model as JSON (`colId`, `sort`).","title":"Agsortmodel"},"description":"Grid sort model as JSON (`colId`, `sort`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/intent/abm/companies/{company_id}/personas":{"get":{"tags":["Signals"],"summary":"Get Abm Company Personas","description":"Who to contact at one account showing intent: its buying committee, persona by persona.","operationId":"get_abm_company_personas_intent_abm_companies__company_id__personas_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Look-back window in days.","default":30,"title":"Days"},"description":"Look-back window in days."},{"name":"export_mode","in":"query","required":false,"schema":{"enum":["signals_only","icp_plus_signals","all_icp_personas"],"type":"string","description":"The same three modes as a keyword's sync config, so this previews what a sync exports.","default":"icp_plus_signals","title":"Export Mode"},"description":"The same three modes as a keyword's sync config, so this previews what a sync exports."},{"name":"icp_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"description":"Score against this ICP.","title":"Icp Id"},"description":"Score against this ICP."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/intent/abm/rollup":{"post":{"tags":["Signals"],"summary":"Rollup Abm Companies","description":"Account strength, high-intent flag and persona coverage for up to 500 named companies.\n\nA read: POST only because the id list is a body. Returned under `rollups`,\nkeyed by company id.","operationId":"rollup_abm_companies_intent_abm_rollup_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AbmRollupRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/intent/contacts/metadata":{"post":{"tags":["Signals"],"summary":"Save Intent To Contact Metadata","description":"Write each contact's resolved intent onto the contact record, in the background.\n\n202: the work runs after the response, on THIS request's own background\ntasks. The org is always the key's own; `force_update` overwrites intent\nmetadata already present instead of only filling gaps.","operationId":"save_intent_to_contact_metadata_intent_contacts_metadata_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SaveIntentToMetadataRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/intent/pages-by-domain":{"post":{"tags":["Intent"],"summary":"Pages By Domain","description":"Every indexed page on a competitor domain (and its subdomains).\n\nQueries ClickHouse `intent.crawl_pages` directly via a\n`domain_root = X OR domain_root LIKE '%.X'` filter. Orders by\n`commercial_score DESC`. Primary consumer: compete-tracking keyword\nsetup - avoids polluting a keyword row with news articles that only\nmention the competitor.","operationId":"pages_by_domain_intent_pages_by_domain_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PagesByDomainRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PagesByDomainResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/intent/pages/search":{"post":{"tags":["Intent"],"summary":"Pages Search","description":"Text / semantic / hybrid search across the intent-enriched page index.\n\nHonors the same operator syntax the internal search box supports:\n`site:<domain>`, `intitle:X`, `inurl:X`, `type:blog`, `audience:b2b`,\n`-exclude`, or just a bare domain for domain-mode.","operationId":"pages_search_intent_pages_search_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PagesSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PagesSearchResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/intent/pages/visitors":{"post":{"tags":["Intent"],"summary":"Pages Visitors","description":"Resolve the people who visited a specific page URL.\n\nBacked by the same S1 -> S2 chain the FE drill-down uses. Returns\nHEM, profile fields (verified), and a `source` tier (verified / b2b /\nb2c / company / anonymous) so the caller can filter confidence.","operationId":"pages_visitors_intent_pages_visitors_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PagesVisitorsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/intent/pages/contacts":{"post":{"tags":["Intent"],"summary":"Pages Contacts","description":"Aggregated, deduplicated resolved contacts across a URL list.\n\nOne batched HEM pull, then the 4-path identity fan-out. Used to\npre-populate the `contacts` array on a save-from-search keyword so the\nrow shows contact counts immediately (not after the daily resolver).","operationId":"pages_contacts_intent_pages_contacts_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PagesContactsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/intent/pages/visitor-counts":{"post":{"tags":["Intent"],"summary":"Pages Visitor Counts","description":"Batched unique-visitor count per page URL.\n\nReads the pre-aggregated `intent.url_visitor_counts` MV first; falls\nback to the raw `intent.optimized_signals_v1` if the MV doesn't exist\nyet. Fast enough to call with thousands of URLs.","operationId":"pages_visitor_counts_intent_pages_visitor_counts_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PagesVisitorCountsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/intent/url-companies":{"post":{"tags":["Intent"],"summary":"Url Companies","description":"Companies whose people visited a single URL, with a B2B/B2C split.\n\nAggregated from `{org_id}.intent_resolved`. Contact-resolved companies\nonly - IP-only company resolution is a separate treatment and is not\nincluded here.\n\nThe response shape is field-for-field identical to the main-app\n`POST /intent-search/url-companies` that backs the FE drill-down; key\nparity between the two is locked by\n`developer_api/tests/test_intent_url_companies_api.py`.\n\nFailure semantics deliberately differ from that main-app route: it\nswallows lookup errors and returns an empty result, which over this\nsurface would be indistinguishable from \"nobody visited\". Consistent\nwith its `/intent/pages/*` siblings, this raises 503 instead so a caller\ncan tell a degraded backend from a genuine zero.","operationId":"url_companies_intent_url_companies_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UrlCompaniesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/intent/stats":{"get":{"tags":["Intent"],"summary":"Intent Stats","description":"Index-coverage stats: document count + size.\n\nUseful for health checks before committing to a compete-tracking program.","operationId":"intent_stats_intent_stats_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/intent/keywords/list":{"post":{"tags":["Intent"],"summary":"Keywords List","description":"All compete-tracking keyword rows for the org.\n\nEach row carries `total_resolved_contacts` and\n`total_resolved_companies` so the caller can rank rows by actual\ncompete intelligence delivered.","operationId":"keywords_list_intent_keywords_list_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/KeywordsListRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/intent/keywords/create-from-domain":{"post":{"tags":["Intent"],"summary":"Keywords Create From Domain","description":"One-shot compete-tracking keyword create.\n\nUnder the hood:\n  1. `pages-by-domain` -> on-domain / subdomain URLs only\n  2. `contacts` -> pre-resolved people across those URLs\n  3. `save-from-search` -> persists the keyword row with both\n\nThe off-domain guard is strict: every page returned from step 1 is\nre-checked against `^(.+\\.)?<domain>$` before save, so nothing that\nisn't actually on the competitor's site can slip in.","operationId":"keywords_create_from_domain_intent_keywords_create_from_domain_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/KeywordCreateFromDomainRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_KeywordCreateFromDomainResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/intent/keywords/create-from-search":{"post":{"tags":["Intent"],"summary":"Keywords Create From Search","description":"Bulk-create compete-tracking keywords from free-text queries.\n\nThe array/free-text sibling of ``create-from-domain``. For EACH keyword\n(max 10, processed sequentially) it runs:\n\n  1. ``pages/search``            - text/semantic search of the intent index\n  2. ``contacts_for_urls``       - resolve people who visited those pages\n  3. ``save_keyword_from_search``- persist the keyword + URLs + contacts\n\nEach keyword is isolated: a failure on one yields ``status=\"error\"`` for\nthat item and never fails the whole batch. Empty / whitespace-only entries\nand in-request duplicates (case-insensitive, trimmed) are ``status=\"skipped\"``\nbefore any search/resolve work.\n\nNOTE - not idempotent across requests: re-posting the same keyword text in a\nLATER request replaces the prior saved row and returns a NEW ``keyword_id``\n(the underlying save is replace-on-save for an exact keyword+filters match).","operationId":"keywords_create_from_search_intent_keywords_create_from_search_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/KeywordsCreateFromSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_KeywordsCreateFromSearchResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/intent/keywords/add":{"post":{"tags":["Intent"],"summary":"Keywords Add","description":"Bulk-add plain compete-tracking keyword rows (web-UI \"Add keywords\" parity).\n\nThin public proxy over the SAME handler the graph8 web UI's Buyer Intent >\nKeywords bulk-add uses (``POST /intent/keywords/add-keywords`` internally).\nOne deliberate strictness on top of the UI path: entries are trimmed of\nleading/trailing whitespace before saving (the UI screen saves them raw).\nEverything else matches the UI path:\n\n- Keywords are stored lowercased; the response carries the stored text.\n- A keyword that already exists for this org + ``signal_type`` (and is not\n  soft-deleted) is skipped silently by the handler; this route reports it\n  as ``skipped`` with reason ``already_exists``. Soft-deleted keywords can\n  be re-added.\n- For ``signal_type='intent'`` each NEWLY created keyword fires a\n  background SERP fetch that seeds its URL set asynchronously - URLs and\n  resolved contacts/companies appear later, not in this response.\n- Unlike ``create-from-search`` this saves the plain phrase only (no\n  search seeding, no ``search_filters``); use\n  ``/keywords/{id}/filters`` afterwards to set per-keyword filters.","operationId":"keywords_add_intent_keywords_add_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/KeywordsAddRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_KeywordsAddResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/intent/keywords/{keyword_id}/urls":{"post":{"tags":["Intent"],"summary":"Keyword Urls","description":"URLs linked to a compete-tracking keyword (data4seo_task_results).","operationId":"keyword_urls_intent_keywords__keyword_id__urls_post","parameters":[{"name":"keyword_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Keyword Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/KeywordDetailRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/intent/keywords/{keyword_id}/contacts":{"post":{"tags":["Intent"],"summary":"Keyword Contacts","description":"People resolved against a keyword's URL set (intent_resolved).","operationId":"keyword_contacts_intent_keywords__keyword_id__contacts_post","parameters":[{"name":"keyword_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Keyword Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/KeywordDetailRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/intent/keywords/{keyword_id}/companies":{"post":{"tags":["Intent"],"summary":"Keyword Companies","description":"Companies resolved against a keyword's URL set (intent_resolved).","operationId":"keyword_companies_intent_keywords__keyword_id__companies_post","parameters":[{"name":"keyword_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Keyword Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/KeywordDetailRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/intent/keywords/{keyword_id}/filters":{"post":{"tags":["Intent"],"summary":"Keyword Update Filters","description":"Replace a keyword's `search_filters` JSON.\n\n404 when the keyword does not exist for this org or was deleted (IN-07:\nthe bare ALTER matched no row and still answered \"success\").","operationId":"keyword_update_filters_intent_keywords__keyword_id__filters_post","parameters":[{"name":"keyword_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Keyword Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/KeywordFiltersUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/hiring-signals/jobs":{"post":{"tags":["Signals"],"summary":"Search Hiring Jobs","description":"Raw job postings matching the keywords. The default view.","operationId":"search_hiring_jobs_hiring_signals_jobs_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/JobSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_JobSearchResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/hiring-signals/companies":{"post":{"tags":["Signals"],"summary":"Search Hiring Companies","description":"The companies behind those postings, rolled up.\n\n`per_company_cap` bounds how many of one company's postings count toward\nits score, so a company with 400 open roles does not drown the ranking.","operationId":"search_hiring_companies_hiring_signals_companies_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/JobSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_JobSearchResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/hiring-signals/decision-makers":{"post":{"tags":["Signals"],"summary":"Search Hiring Decision Makers","description":"People to talk to at the hiring companies.\n\nScoped by the `persona_*` filters, capped per company by\n`contacts_per_company` - the point is a shortlist per account, not every\nemployee.","operationId":"search_hiring_decision_makers_hiring_signals_decision_makers_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/JobSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_JobSearchResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/hiring-signals/recruiters":{"post":{"tags":["Signals"],"summary":"Search Hiring Recruiters","description":"The recruiters who posted the matching jobs.\n\nPaged by `recruiter_limit`/`recruiter_offset`, INDEPENDENTLY of the\ncompanies paging: one recruiter can serve many companies, so the two\ncounts diverge and paging one must not move the other.","operationId":"search_hiring_recruiters_hiring_signals_recruiters_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/JobSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_JobSearchResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/hiring-signals/aggregators":{"post":{"tags":["Signals"],"summary":"Search Hiring Aggregators","description":"What `exclude_aggregators` suppressed.\n\nThe audit trail for the suppression: a job board is not a company that is\nhiring, but a caller should be able to see what was dropped rather than\ntake it on trust.","operationId":"search_hiring_aggregators_hiring_signals_aggregators_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/JobSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_JobSearchResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/hiring-signals/companies/{linkedin_company_id}/jobs":{"get":{"tags":["Signals"],"summary":"List Company Hiring Jobs","description":"Recent postings at one company.","operationId":"list_company_hiring_jobs_hiring_signals_companies__linkedin_company_id__jobs_get","parameters":[{"name":"linkedin_company_id","in":"path","required":true,"schema":{"type":"integer","description":"LinkedIn company id (lcid).","title":"Linkedin Company Id"},"description":"LinkedIn company id (lcid)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":50,"title":"Limit"}},{"name":"window_days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"default":60,"title":"Window Days"}},{"name":"include_subsidiaries","in":"query","required":false,"schema":{"type":"boolean","description":"Expand the lcid to its subsidiaries, so a parent company's view surfaces postings made under a child lcid. On by default because the parent is usually who the customer is selling to.","default":true,"title":"Include Subsidiaries"},"description":"Expand the lcid to its subsidiaries, so a parent company's view surfaces postings made under a child lcid. On by default because the parent is usually who the customer is selling to."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_JobSearchResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/hiring-signals/companies/{linkedin_company_id}/linkedin-posts":{"get":{"tags":["Signals"],"summary":"List Company Linkedin Posts","description":"Recent organic LinkedIn posts from one company.\n\n`window_days` is optional here, unlike on the jobs endpoint: an omitted\nwindow means \"newest regardless of age\", not \"default of 60\". Defaulting\nit would silently hide a company that posts rarely.","operationId":"list_company_linkedin_posts_hiring_signals_companies__linkedin_company_id__linkedin_posts_get","parameters":[{"name":"linkedin_company_id","in":"path","required":true,"schema":{"type":"integer","description":"LinkedIn company id (lcid).","title":"Linkedin Company Id"},"description":"LinkedIn company id (lcid)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"window_days","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","maximum":3650,"minimum":1},{"type":"null"}],"description":"Optional age cap in days. OMIT to get the newest posts regardless of age.","title":"Window Days"},"description":"Optional age cap in days. OMIT to get the newest posts regardless of age."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_JobSearchResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/hiring-signals/companies/job-counts":{"post":{"tags":["Signals"],"summary":"Get Company Job Counts","description":"Active-job counts for a page of companies, in one call.\n\nCapped at 1000 lcids: this is for decorating a grid page, not scanning a\ncorpus.","operationId":"get_company_job_counts_hiring_signals_companies_job_counts_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CompanyJobCountsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/hiring-signals/jobs/{job_id}":{"get":{"tags":["Signals"],"summary":"Get Hiring Job Details","description":"One posting, with its company, its recruiter and the company's other jobs.","operationId":"get_hiring_job_details_hiring_signals_jobs__job_id__get","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"integer","description":"Job id.","title":"Job Id"},"description":"Job id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_JobDetails_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/hiring-signals/companies/resolve-ids":{"post":{"tags":["Signals"],"summary":"Resolve Hiring Company Ids","description":"Turn LinkedIn company ids into graph8 company ids.\n\nThis is the step that makes a Hiring Signals result usable: the search\nreturns lcids, and building a list or enrolling a sequence needs graph8\nids. The handler caps the input server-side regardless of what is sent.","operationId":"resolve_hiring_company_ids_hiring_signals_companies_resolve_ids_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ResolveCompanyIdsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/hiring-signals/job-changes":{"get":{"tags":["Signals"],"summary":"List Job Change Signals","description":"Contacts who changed employer.\n\nIdentifying fields are REDACTED unless the key's user holds a Signals\nwrite capability - these are named people who moved, which is exactly the\ndata a read-only role is not meant to export. The capability is resolved\nfrom the same principal the browser resolves it from.","operationId":"list_job_change_signals_hiring_signals_job_changes_get","parameters":[{"name":"contact_id","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Filter to a single contact.","title":"Contact Id"},"description":"Filter to a single contact."},{"name":"listener_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter to a single Talent Moves listener.","title":"Listener Id"},"description":"Filter to a single Talent Moves listener."},{"name":"since","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only events detected at or after this ISO timestamp.","title":"Since"},"description":"Only events detected at or after this ISO timestamp."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_JobChangeSignalsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/hiring-signals/job-changes/match":{"post":{"tags":["Signals"],"summary":"Match Job Change Signals","description":"Which of these LinkedIn profiles changed job in the last 90 days.\n\nA lookup, not a search: it answers a question about a list the caller\nalready has, which is why it takes URLs rather than filters.","operationId":"match_job_change_signals_hiring_signals_job_changes_match_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/JobChangeMatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_JobChangeSignalsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/social-listeners":{"post":{"tags":["Signals"],"summary":"Create Listener","description":"Start watching something.\n\nTHIS CAN SPEND CREDITS: a `brand` listener with no `query` has one built by\nan LLM call, which is charged. Supply `query`, or call\n`POST /social-listeners/queries/generate` first, to see what you are\ncommitting to.\n\nA `user` listener additionally resolves `target_handle` against the\nplatform, which consumes the org's X API quota.\n\nSet `monthly_credit_cap` unless you have set an org-wide one - it is the\nonly per-listener bound on what this costs.","operationId":"create_listener_social_listeners_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateListenerRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"},"get":{"tags":["Signals"],"summary":"List Listeners","description":"Every listener in the org, with its state.","operationId":"list_listeners_social_listeners_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/social-listeners/preview-cost":{"post":{"tags":["Signals"],"summary":"Preview Listener Cost","description":"What a listener WOULD cost per month. CHARGES NOTHING.\n\nA pure estimate: it samples at most ten results to project a posts-per-day\nrate, caches the answer for an hour, and returns arithmetic.\n`credits_per_month_estimate` is a projection for a listener that does not\nexist yet, not a debit.\n\nTiered `read` for that reason, so a read-only key can find out what\nsomething costs before anyone commits to it. POST only because the query is\na body.","operationId":"preview_listener_cost_social_listeners_preview_cost_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PreviewCostRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/social-listeners/bulk-from-list":{"post":{"tags":["Signals"],"summary":"Bulk Create Listeners From List","description":"One `user` listener per social profile on a graph8 list.\n\nNo platform lookup happens here - handles are resolved lazily by the\npolling worker on first poll, so this does not burn one API call per row at\ncreation time.","operationId":"bulk_create_listeners_from_list_social_listeners_bulk_from_list_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BulkCreateFromListRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/social-listeners/auto-seed-status":{"get":{"tags":["Signals"],"summary":"Get Auto Seed Status","description":"How the asynchronous `/auto-seed/all` run is going.\n\nThe only way to see what that call did: it answers 202 before any of the\nseeding, or any of the credit spend, has happened.","operationId":"get_auto_seed_status_social_listeners_auto_seed_status_get","parameters":[{"name":"job_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"A job id from `/auto-seed/all`. Omit for the most recent run.","title":"Job Id"},"description":"A job id from `/auto-seed/all`. Omit for the most recent run."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/social-listeners/source-lists":{"get":{"tags":["Signals"],"summary":"List Source Lists","description":"graph8 lists that can be used as the source for `/bulk-from-list`.","operationId":"list_source_lists_social_listeners_source_lists_get","parameters":[{"name":"audience_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter to one audience type.","title":"Audience Type"},"description":"Filter to one audience type."},{"name":"active_only","in":"query","required":false,"schema":{"type":"boolean","description":"Only lists still in use.","default":true,"title":"Active Only"},"description":"Only lists still in use."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/social-listeners/stats":{"get":{"tags":["Signals"],"summary":"Get Social Stats","description":"Match counts, listener counts and platform spend to date.\n\nThe number to watch against `monthly_credit_cap`.","operationId":"get_social_stats_social_listeners_stats_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/social-listeners/settings":{"get":{"tags":["Signals"],"summary":"Get Social Settings","description":"Org-wide social listening settings, including every spend ceiling.","operationId":"get_social_settings_social_listeners_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Signals"],"summary":"Update Social Settings","description":"Change the org's spend ceilings and capture rules.\n\nADMIN ONLY, and gated twice for two different reasons. The app declares\n`require_signals_write` as a dependency AND checks\n`user.has_role_in_org(org_id, \"Admin\")` in its BODY. That second check\nreads `User.roles`, which `get_api_user` never populates - so for an API\nkey it answers False no matter who minted it. `require_org_admin` is the\nAPI-key-native half and `with_org_role` makes the app's own half answer\ncorrectly rather than refusing everyone.\n\nThis is the surface that BOUNDS what social listening costs. Raising\n`monthly_credit_cap` or turning `auto_pause_on_cap` off removes the brake.","operationId":"update_social_settings_social_listeners_settings_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PatchSocialSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/social-listeners/queries/generate":{"post":{"tags":["Signals"],"summary":"Generate Listener Query","description":"Turn a plain-English description into a platform-native query.\n\nTHIS SPENDS CREDITS - it is an LLM call. It returns the query rather than\ncreating a listener, so the query can be read, edited and reused across\nseveral listeners for the price of one generation.","operationId":"generate_listener_query_social_listeners_queries_generate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/GenerateQueryRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/social-listeners/auto-seed/brand":{"post":{"tags":["Signals"],"summary":"Auto Seed Brand Listener","description":"Create a brand listener from the org's brand documents.\n\nSPENDS CREDITS - an LLM call extracts the brand and product names. The\ncharge happens BEFORE the listeners are inserted, so a failure after\nextraction still costs. 400 if the org has no brand brief to read.","operationId":"auto_seed_brand_listener_social_listeners_auto_seed_brand_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/social-listeners/auto-seed/competitors":{"post":{"tags":["Signals"],"summary":"Auto Seed Competitor Listeners","description":"Create competitor listeners from the org's brand documents.\n\nSPENDS CREDITS - an LLM call extracts the competitor names, charged before\nthe listeners are inserted.","operationId":"auto_seed_competitor_listeners_social_listeners_auto_seed_competitors_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/social-listeners/auto-seed/keywords":{"post":{"tags":["Signals"],"summary":"Auto Seed Keyword Listeners","description":"Create keyword listeners from the org's existing keyword intelligence.\n\nThe ONLY auto-seed that charges nothing: it reads keywords that were\nalready gathered rather than asking an LLM for new ones. Start here.","operationId":"auto_seed_keyword_listeners_social_listeners_auto_seed_keywords_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/social-listeners/auto-seed/engagement":{"post":{"tags":["Signals"],"summary":"Auto Seed Engagement Listeners","description":"Create ICP-shaped engagement listeners.\n\nSPENDS CREDITS - one LLM call produces two or three query buckets, charged\nONCE regardless of how many channels the buckets fan out to.\n\nOmit the body entirely to take the app's own default channel set (X alone)\nrather than this contract freezing a copy of it.","operationId":"auto_seed_engagement_listeners_social_listeners_auto_seed_engagement_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/SeedChannelsRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/social-listeners/auto-seed/all":{"post":{"tags":["Signals"],"summary":"Auto Seed All Listeners","description":"Run every auto-seed in one go. ASYNCHRONOUS, AND IT SPENDS CREDITS.\n\n202 is returned BEFORE any seeding happens. The brand, competitor and\nengagement stages each make their own charged LLM call afterwards, in a\nbackground task - so up to three charges land after this response, and a\ncaller that only reads the response body will not see any of them. Poll\n`GET /social-listeners/auto-seed-status` with the returned `job_id`.\n\nEach stage fails independently: a partial result is normal and is not an\nerror.\n\n409 if a run is already in flight.","operationId":"auto_seed_all_listeners_social_listeners_auto_seed_all_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/SeedChannelsRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/social-listeners/posts/search":{"post":{"tags":["Signals"],"summary":"Search Matched Posts","description":"Posts the listeners have already matched.\n\nA PAGINATED DATABASE READ. It makes no live platform call and spends\nnothing - the fetching is done by the polling worker, not by this call. The\napp spells it `/fetch`, which reads like it goes and gets them; it does\nnot, and the path here says so.\n\nTiered `read` for the same reason: a key granted \"read my signals\" has to\nbe able to read a matched post.","operationId":"search_matched_posts_social_listeners_posts_search_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SearchPostsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/social-listeners/posts/{post_id}/engagements/search":{"post":{"tags":["Signals"],"summary":"Search Post Engagements","description":"Who commented on or reacted to one matched post.\n\nAlso a paginated database read - the engagements were stored by the worker,\nand only when `fetch_engagements` is on for that channel. An empty result\ncan mean \"nobody engaged\" OR \"engagement fetching is off\"; check\n`GET /social-listeners/settings`.","operationId":"search_post_engagements_social_listeners_posts__post_id__engagements_search_post","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"The post's platform-native id.","title":"Post Id"},"description":"The post's platform-native id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SearchPostEngagementsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/social-listeners/posts/{post_id}/engagements/add-to-list":{"post":{"tags":["Signals"],"summary":"Add Engagers To List","description":"Turn the people who engaged with a post into a graph8 list.\n\nCREATES CONTACTS. Engagers with no matching graph8 contact are created as\nstubs, so this grows the contact database as well as the list.\n\nSupply `audience_id` for an existing list or `audience_name` to create one.\nThe app does not gate this on `signals:write`; this surface does, because\ncreating contacts from a public post is a write by any reading and the\napp's omission looks like an oversight rather than a decision.","operationId":"add_engagers_to_list_social_listeners_posts__post_id__engagements_add_to_list_post","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"The post's platform-native id.","title":"Post Id"},"description":"The post's platform-native id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AddEngagersToListRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/social-listeners/posts/{post_id}/mark":{"post":{"tags":["Signals"],"summary":"Mark Post","description":"Triage a matched post as reviewed or dismissed.\n\n`platform` is part of the identity, not a filter - the same id means\ndifferent posts on different platforms.","operationId":"mark_post_social_listeners_posts__post_id__mark_post","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"The post's platform-native id.","title":"Post Id"},"description":"The post's platform-native id."},{"name":"platform","in":"query","required":false,"schema":{"enum":["x","linkedin","reddit","instagram","youtube"],"type":"string","description":"Which platform the post id belongs to.","default":"x","title":"Platform"},"description":"Which platform the post id belongs to."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MarkPostRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/social-listeners/posts/{post_id}/save-contact":{"post":{"tags":["Signals"],"summary":"Save Post Author As Contact","description":"Turn one post's author into a graph8 contact.\n\nResolves an existing contact where there is one rather than duplicating.\nNo enrichment happens here and no credit is spent - the contact is created\nfrom what the post already carries.","operationId":"save_post_author_as_contact_social_listeners_posts__post_id__save_contact_post","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"The post's platform-native id.","title":"Post Id"},"description":"The post's platform-native id."},{"name":"platform","in":"query","required":false,"schema":{"enum":["x","linkedin","reddit","instagram","youtube"],"type":"string","default":"x","title":"Platform"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/social-listeners/posts/{post_id}/add-to-sequence":{"post":{"tags":["Signals"],"summary":"Add Post Author To Sequence","description":"Enrol a post's author into a sequence.\n\n202, NOT 200: this resolves the author to a contact and publishes an\nenrolment REQUEST. The sequencer consumes it afterwards, and it is that\nconsumer - not this call - that starts sending to a real person. A 202 here\ndoes not mean the person is enrolled, and it does not mean they are not\nabout to be.","operationId":"add_post_author_to_sequence_social_listeners_posts__post_id__add_to_sequence_post","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"The post's platform-native id.","title":"Post Id"},"description":"The post's platform-native id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AddPostToSequenceRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/social-listeners/posts/by-contact/{contact_id}":{"get":{"tags":["Signals"],"summary":"List Posts By Contact","description":"Everything one graph8 contact has posted that a listener matched.\n\nMatches on the resolved contact link first and falls back to a\ncase-insensitive handle match, so it still finds posts recorded before the\nauthor was resolved to a contact.\n\n404 for a contact outside the key's record scope - the same answer as a\ncontact that does not exist, so the two cannot be told apart.","operationId":"list_posts_by_contact_social_listeners_posts_by_contact__contact_id__get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":100,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/social-listeners/engagements/top-accounts":{"get":{"tags":["Signals"],"summary":"List Top Engaged Accounts","description":"The accounts that engage with you most often.\n\nThe warm-audience view: someone who has commented on four of your posts is\na different prospect from someone who liked one.","operationId":"list_top_engaged_accounts_social_listeners_engagements_top_accounts_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"default":30,"title":"Days"}},{"name":"platform","in":"query","required":false,"schema":{"anyOf":[{"enum":["x","linkedin","reddit","instagram","youtube"],"type":"string"},{"type":"null"}],"title":"Platform"}},{"name":"min_posts","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Only accounts that engaged this often.","default":2,"title":"Min Posts"},"description":"Only accounts that engaged this often."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialCollection_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/social-listeners/integrations/x":{"post":{"tags":["Signals"],"summary":"Connect X Credentials","description":"Store the org's own X developer credentials.\n\nWRITE-ONLY. The key, the secret and the bearer token derived from them are\nencrypted at rest and are never returned - not by this route, and not by\nany other on this surface.\n\nWith credentials stored the org pays X directly and is not bounded by\ngraph8's shared quota. Test them first with\n`POST /social-listeners/integrations/x/test`, which validates without\nstoring anything.","operationId":"connect_x_credentials_social_listeners_integrations_x_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/XApiCredentialsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"},"get":{"tags":["Signals"],"summary":"Get X Integration","description":"Whether the org has its own X credentials stored, and since when.\n\nReports that a connection exists. It does not report what it is - see\n`POST /social-listeners/integrations/x`.","operationId":"get_x_integration_social_listeners_integrations_x_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Signals"],"summary":"Disconnect X Credentials","description":"Remove the org's own X credentials.\n\nTHIS PAUSES LISTENERS. Every active X listener is paused; if graph8's\nshared mode is available they are immediately reactivated under it, with an\nalert per listener. If it is not, they stay paused and stop matching.","operationId":"disconnect_x_credentials_social_listeners_integrations_x_delete","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"intent:delete","x-graph8-lifecycle":"active"}},"/social-listeners/integrations/x/test":{"post":{"tags":["Signals"],"summary":"Test X Credentials","description":"Check credentials against X without storing them.\n\nPersists NOTHING, whether the check passes or fails. Run this before\n`POST /social-listeners/integrations/x` so a typo does not pause every\nlistener the org has.","operationId":"test_x_credentials_social_listeners_integrations_x_test_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/XApiCredentialsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/social-listeners/integrations/x/mode":{"get":{"tags":["Signals"],"summary":"Get X Effective Mode","description":"Which X credentials this org is ACTUALLY polling with, and how much of\nthe shared allowance is left.\n\nNot the same question as `GET /social-listeners/integrations/x`: an org can\nhave credentials stored and still be on shared mode, and an org on shared\nmode is competing for a quota it does not control. This is the number to\nread when listeners stop matching.","operationId":"get_x_effective_mode_social_listeners_integrations_x_mode_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/social-listeners/{listener_id}":{"get":{"tags":["Signals"],"summary":"Get Listener","description":"One listener, with its match count and running credit burn.","operationId":"get_listener_social_listeners__listener_id__get","parameters":[{"name":"listener_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"The listener's id.","title":"Listener Id"},"description":"The listener's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Signals"],"summary":"Update Listener","description":"Partial update. Omitted fields are left alone.\n\n`is_active: false` pauses polling without losing the listener or its\nhistory - the way to stop spend without destroying what has been matched.\n\nChanging `target_handle` on a `user` listener re-resolves the account\nagainst the platform, which consumes X API quota.","operationId":"update_listener_social_listeners__listener_id__patch","parameters":[{"name":"listener_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"The listener's id.","title":"Listener Id"},"description":"The listener's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PatchListenerRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Signals"],"summary":"Delete Listener","description":"Delete a listener.\n\nGated on `signals:delete` specifically, not on `signals:write` - the app\nseparates them, and so does this. To stop the spend without losing the\nmatched posts, PATCH `is_active: false` instead.","operationId":"delete_listener_social_listeners__listener_id__delete","parameters":[{"name":"listener_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"The listener's id.","title":"Listener Id"},"description":"The listener's id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SocialPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"intent:delete","x-graph8-lifecycle":"active"}},"/seo/domains/tracked":{"get":{"tags":["SEO"],"summary":"List Seo Tracked Domains","description":"SPENDS NOTHING. The SEO overview: every saved domain with its last snapshot.\n\nOwn domains first (the primary one first), then the Radar competitors\nshown beside them, each with its saved metrics and 30-day change. Also\ncarries what each PAID refresh would cost (`refresh_credits`,\n`pages_max_credits`, `page_keywords_credits`), so a caller can quote a\nprice without spending anything. An organisation whose SEO storage is\nstill provisioning gets an empty list, matching the app.","operationId":"list_seo_tracked_domains_seo_domains_tracked_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoTrackedDomains_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"},"post":{"tags":["SEO"],"summary":"Add Seo Tracked Domain","description":"SPENDS NOTHING. Save a domain so it can be tracked: keywords, rank checks and snapshots hang off it.\n\nThe domain is lower-cased with `www.` stripped; a scheme or a path is a\n422. 409 once the organisation is at its cap of own domains (see\n`max_own_domains` on `GET /seo/domains/tracked`). The snapshot stays empty\nuntil `POST /seo/domains/tracked/{domain}/refresh` runs.","operationId":"add_seo_tracked_domain_seo_domains_tracked_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SeoAddTrackedDomainRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoTrackedDomainDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"intent:write","x-graph8-lifecycle":"active"}},"/seo/domains/tracked/{domain}":{"get":{"tags":["SEO"],"summary":"Get Seo Tracked Domain","description":"SPENDS NOTHING. One saved domain's snapshot: overview, top keywords, top pages, backlinks.\n\nRendered from what the app last stored; it never calls the provider. 404\nfor a domain this organisation does not track. `snapshot_at` says how\nold the snapshot is; it is null until the domain is first refreshed.","operationId":"get_seo_tracked_domain_seo_domains_tracked__domain__get","parameters":[{"name":"domain","in":"path","required":true,"schema":{"type":"string","description":"A saved domain from `GET /seo/domains/tracked`.","title":"Domain"},"description":"A saved domain from `GET /seo/domains/tracked`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoTrackedDomainDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"},"delete":{"tags":["SEO"],"summary":"Remove Seo Tracked Domain","description":"SPENDS NOTHING. Stop tracking a domain and delete its saved snapshot.\n\nGated on the Signals DELETE permission, as the app gates it. 404 for a\ndomain this organisation does not track; 409 for the last remaining own\ndomain.","operationId":"remove_seo_tracked_domain_seo_domains_tracked__domain__delete","parameters":[{"name":"domain","in":"path","required":true,"schema":{"type":"string","description":"A saved domain from `GET /seo/domains/tracked`.","title":"Domain"},"description":"A saved domain from `GET /seo/domains/tracked`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoRemovedDomain_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"intent:delete","x-graph8-lifecycle":"active"}},"/seo/domains/tracked/{domain}/pages":{"get":{"tags":["SEO"],"summary":"List Seo Domain Pages","description":"SPENDS NOTHING. The saved ranking pages of a tracked domain, paged and sorted.\n\nRead only: it never calls the provider. `refreshed_at` is null when the\npages were never fetched (fetching them is a paid action in the app).\nAn unknown sort column is a 422 naming the allowed ones.","operationId":"list_seo_domain_pages_seo_domains_tracked__domain__pages_get","parameters":[{"name":"domain","in":"path","required":true,"schema":{"type":"string","description":"A saved domain from `GET /seo/domains/tracked`.","title":"Domain"},"description":"A saved domain from `GET /seo/domains/tracked`."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","maximum":1000,"minimum":0,"description":"Rows to skip (the saved pages are capped at 1,000).","default":0,"title":"Offset"},"description":"Rows to skip (the saved pages are capped at 1,000)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Rows to return.","default":50,"title":"Limit"},"description":"Rows to return."},{"name":"sort","in":"query","required":false,"schema":{"type":"string","description":"Sort column: estimated_traffic, ranking_keywords_count, best_position, url, traffic_change_30d or audit_issues.","default":"estimated_traffic","title":"Sort"},"description":"Sort column: estimated_traffic, ranking_keywords_count, best_position, url, traffic_change_30d or audit_issues."},{"name":"order","in":"query","required":false,"schema":{"enum":["asc","desc"],"type":"string","default":"desc","title":"Order"}},{"name":"q","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"description":"Only pages whose URL contains this text.","title":"Q"},"description":"Only pages whose URL contains this text."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoDomainPages_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/seo/domains/tracked/{domain}/primary":{"post":{"tags":["SEO"],"summary":"Set Seo Primary Domain","description":"SPENDS NOTHING. Make a saved domain the organisation's primary one (listed first, the default for reads).\n\n404 for a domain this organisation does not track.","operationId":"set_seo_primary_domain_seo_domains_tracked__domain__primary_post","parameters":[{"name":"domain","in":"path","required":true,"schema":{"type":"string","description":"A saved domain from `GET /seo/domains/tracked`.","title":"Domain"},"description":"A saved domain from `GET /seo/domains/tracked`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoTrackedDomainDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"intent:write","x-graph8-lifecycle":"active"}},"/seo/domains/tracked/{domain}/refresh":{"post":{"tags":["SEO"],"summary":"Refresh Seo Tracked Domain","description":"SPENDS CREDITS. Refresh a saved domain's snapshot: overview, backlinks and a keyword sample.\n\nAt most `refresh_credits` (see `GET /seo/domains/tracked`); that maximum\nis held before any provider call, so a balance that cannot cover it is a\n402 naming the amount. A retry within minutes of a successful refresh\nreturns the saved snapshot for free (`refreshed` is false). A provider\noutage is a 502 that says so.","operationId":"refresh_seo_tracked_domain_seo_domains_tracked__domain__refresh_post","parameters":[{"name":"domain","in":"path","required":true,"schema":{"type":"string","description":"A saved domain from `GET /seo/domains/tracked`.","title":"Domain"},"description":"A saved domain from `GET /seo/domains/tracked`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoTrackedDomainDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/seo/keywords/research":{"post":{"tags":["SEO"],"summary":"Research Seo Keywords","description":"SPENDS CREDITS. Keyword ideas around a seed, from the paid data provider.\n\n`mode` picks the provider report: `ideas`, `related`, `suggestions`, or\n`auto` to let the app choose. Rows come back in that report's own shape.\n\nRuns the app's per-organisation provider rate limit (429 past it) and its\nfail-closed credit check (402 when the balance is exhausted) before\nanything is fetched. A provider outage is a 502 that says so.","operationId":"research_seo_keywords_seo_keywords_research_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SeoResearchKeywordsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoResearchKeywordsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/seo/domains/{domain}/overview":{"get":{"tags":["SEO"],"summary":"Get Seo Domain Overview","description":"SPENDS CREDITS. A domain's organic footprint: overview, top keywords, top pages.\n\nA GET that costs money, so it is tiered `billable` rather than `read` -\nreading rank history and buying a domain report are not the same grant.\n`data_freshness` labels how old the provider's view is. The domain is\nvalidated first: a scheme or a path is a 422, before any credit is checked.","operationId":"get_seo_domain_overview_seo_domains__domain__overview_get","parameters":[{"name":"domain","in":"path","required":true,"schema":{"type":"string","description":"A bare domain - no scheme, no path. `www.` is stripped.","title":"Domain"},"description":"A bare domain - no scheme, no path. `www.` is stripped."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoDomainOverviewResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/seo/domains/{domain}/backlinks":{"get":{"tags":["SEO"],"summary":"Get Seo Domain Backlinks","description":"SPENDS CREDITS. A domain's backlink profile: authority, totals, dofollow / nofollow split.\n\nSame shape as the overview: `billable` despite being a GET, domain\nvalidated before the credit check, provider outage as a 502.","operationId":"get_seo_domain_backlinks_seo_domains__domain__backlinks_get","parameters":[{"name":"domain","in":"path","required":true,"schema":{"type":"string","description":"A bare domain - no scheme, no path. `www.` is stripped.","title":"Domain"},"description":"A bare domain - no scheme, no path. `www.` is stripped."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoBacklinksOverview_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/seo/rank-tracking/keywords":{"post":{"tags":["SEO"],"summary":"Save Seo Tracked Keywords","description":"SPENDS NOTHING NOW. Start tracking up to 100 keywords for a domain.\n\nThe rank checks themselves run in the background worker on the chosen\n`cadence`; saving enrols the organisation in that worker's tick. The\nsaved rows come back with whatever the worker has already recorded.\nDuplicates of an existing keyword are refused with a 422 naming them.","operationId":"save_seo_tracked_keywords_seo_rank_tracking_keywords_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SeoSaveTrackedKeywordsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_List_SeoTrackedKeyword__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"intent:write","x-graph8-lifecycle":"active"}},"/seo/rank-tracking":{"get":{"tags":["SEO"],"summary":"List Seo Tracked Keywords","description":"SPENDS NOTHING. The keywords this organisation tracks, with their latest rank.\n\nAn organisation whose SEO storage is still provisioning gets an empty\nlist rather than an error, matching the app.","operationId":"list_seo_tracked_keywords_seo_rank_tracking_get","parameters":[{"name":"domain","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only keywords tracked for this domain.","title":"Domain"},"description":"Only keywords tracked for this domain."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_List_SeoTrackedKeyword__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/seo/rank-tracking/keywords/remove":{"post":{"tags":["SEO"],"summary":"Remove Seo Tracked Keywords","description":"SPENDS NOTHING. Stop tracking up to 100 keywords, by id.\n\nA POST rather than a DELETE because it takes a batch of ids in the body,\nthe same shape the app uses. Gated on the Signals DELETE permission, as\nthe app gates it. Ids that are not this organisation's are simply not\nremoved, and the count says how many were.","operationId":"remove_seo_tracked_keywords_seo_rank_tracking_keywords_remove_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SeoRemoveTrackedKeywordsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoRemovedKeywords_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"intent:write","x-graph8-lifecycle":"active"}},"/seo/rank-tracking/{keyword_id}/history":{"get":{"tags":["SEO"],"summary":"Get Seo Rank History","description":"SPENDS NOTHING. One tracked keyword's rank, snapshot by snapshot.\n\n`days` bounds the window at 365. A keyword that is not this\norganisation's has no snapshots, so the answer is an empty history rather\nthan a probe.","operationId":"get_seo_rank_history_seo_rank_tracking__keyword_id__history_get","parameters":[{"name":"keyword_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"A tracked keyword id from `GET /seo/rank-tracking`.","title":"Keyword Id"},"description":"A tracked keyword id from `GET /seo/rank-tracking`."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"How far back to read snapshots.","default":90,"title":"Days"},"description":"How far back to read snapshots."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoRankHistory_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/seo/rank-tracking/keywords/tags":{"patch":{"tags":["SEO"],"summary":"Set Seo Keyword Tags","description":"SPENDS NOTHING. Replace the tags on up to 100 tracked keywords (an empty list clears them).\n\nUp to 10 tags of 60 characters each. Ids that are not this\norganisation's are not touched, and `updated` says how many were.","operationId":"set_seo_keyword_tags_seo_rank_tracking_keywords_tags_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SeoSetKeywordTagsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoUpdatedKeywords_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"intent:write","x-graph8-lifecycle":"active"}},"/seo/rank-tracking/keywords/check":{"post":{"tags":["SEO"],"summary":"Check Seo Keywords Now","description":"SPENDS CREDITS. Re-check the chosen keywords' rank now, whatever their cadence.\n\nOne rank-check credit per successful check, charged by the check itself.\nThe checks run in the background: `accepted` says how many were queued,\nand `GET /seo/rank-tracking` shows each new rank as it lands. 402 when the\nbalance is exhausted, 429 past the per-organisation provider limit.","operationId":"check_seo_keywords_now_seo_rank_tracking_keywords_check_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SeoCheckKeywordsNowRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoCheckKeywordsNowResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"}},"/seo/rank-tracking/keywords/cadence":{"patch":{"tags":["SEO"],"summary":"Set Seo Keyword Cadence","description":"SPENDS NOTHING NOW. Change how often up to 100 tracked keywords re-check: daily, weekly or manual.\n\nDaily and weekly re-checks charge credits on a timer, so turning them on\nalso needs the Signals RUN permission (403 without it); switching to\n`manual` needs only the write grant. Enrols the organisation in the\nbackground worker, which re-checks what is due.","operationId":"set_seo_keyword_cadence_seo_rank_tracking_keywords_cadence_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SeoSetKeywordCadenceRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoUpdatedKeywords_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"intent:write","x-graph8-lifecycle":"active"}},"/seo/rank-tracking/share-of-voice":{"get":{"tags":["SEO"],"summary":"Get Seo Share Of Voice","description":"SPENDS NOTHING. Share of voice: tracked keywords weighted by a click-through curve, against the top 10.\n\nComputed from the latest stored rank checks; no provider call.\n`keywords_with_serp` of `keywords_counted` says how much of the set had a\nstored result page, and `confidence` says how far to trust the share.","operationId":"get_seo_share_of_voice_seo_rank_tracking_share_of_voice_get","parameters":[{"name":"domain","in":"query","required":true,"schema":{"type":"string","minLength":3,"maxLength":255,"description":"A bare domain - no scheme, no path.","title":"Domain"},"description":"A bare domain - no scheme, no path."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoShareOfVoice_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/seo/audits":{"post":{"tags":["SEO"],"summary":"Start Seo Audit","description":"SPENDS CREDITS. Start a site audit of up to `max_pages` pages.\n\nCredits are RESERVED up front, sized by `max_pages`, and charged as the\ncrawl completes - `credits_charged` on the audit says what was. 402 when\nthe balance cannot cover the reservation, 409 when an audit of this domain\nis already running, 503 when the credit service cannot take the hold.\n\nThe audit runs in the background; poll `GET /seo/audits/{audit_id}` and\nread `state`, which explains where it is in plain language and whether it\ncan be run again.","operationId":"start_seo_audit_seo_audits_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SeoStartAuditRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoAudit_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"},"get":{"tags":["SEO"],"summary":"List Seo Audits","description":"SPENDS NOTHING. This organisation's audits, newest first.","operationId":"list_seo_audits_seo_audits_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":20,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_List_SeoAudit__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/seo/audits/ai-readiness":{"get":{"tags":["SEO"],"summary":"Get Seo Ai Readiness","description":"SPENDS NOTHING. Is the site readable by AI assistants: llms.txt, AI crawlers in robots.txt, homepage JSON-LD.\n\nFree checks fetched live from the site, under the per-organisation rate\nlimit. Declared before `/seo/audits/{audit_id}` so the literal wins.","operationId":"get_seo_ai_readiness_seo_audits_ai_readiness_get","parameters":[{"name":"domain","in":"query","required":true,"schema":{"type":"string","minLength":3,"maxLength":255,"description":"A bare domain - no scheme, no path.","title":"Domain"},"description":"A bare domain - no scheme, no path."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoAiReadiness_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/seo/audits/{audit_id}":{"get":{"tags":["SEO"],"summary":"Get Seo Audit","description":"SPENDS NOTHING. One audit, with its plain-language `state`. 404 if it is\nnot this organisation's.","operationId":"get_seo_audit_seo_audits__audit_id__get","parameters":[{"name":"audit_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Audit Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoAudit_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/seo/audits/{audit_id}/issues":{"get":{"tags":["SEO"],"summary":"Get Seo Audit Issues","description":"SPENDS NOTHING. The issues an audit found, grouped by type and severity,\neach with the URLs it affects.","operationId":"get_seo_audit_issues_seo_audits__audit_id__issues_get","parameters":[{"name":"audit_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Audit Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoAuditIssues_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/seo/fixes":{"get":{"tags":["SEO"],"summary":"List Seo Fixes","description":"SPENDS NOTHING. The SEO fixes queued for a coding agent, with exact instructions and code.\n\nOnly fixes the organisation approved for its coding agent appear (status `ready_for_agent`), plus any whose\nclaim expired. Each carries the page, ordered steps, the snippets to add and how success is checked.\n`agents_md` is the same list as an AGENTS.md document.","operationId":"list_seo_fixes_seo_fixes_get","parameters":[{"name":"domain","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"description":"Only fixes for this domain.","title":"Domain"},"description":"Only fixes for this domain."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Fixes to return, most severe first.","default":20,"title":"Limit"},"description":"Fixes to return, most severe first."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoAgentFixQueue_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/seo/fixes/agent-handoff":{"get":{"tags":["SEO"],"summary":"Get Seo Agent Handoff","description":"SPENDS NOTHING. AGENTS.md and CLAUDE.md for the queued fixes plus one-line MCP setup for Claude Code and Cursor.\n\nThe setup lines connect the coding agent to graph8 over MCP so it can list, claim and complete fixes itself.","operationId":"get_seo_agent_handoff_seo_fixes_agent_handoff_get","parameters":[{"name":"domain","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"description":"Only fixes for this domain.","title":"Domain"},"description":"Only fixes for this domain."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoAgentHandoff_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/seo/fixes/{fix_id}/pack":{"get":{"tags":["SEO"],"summary":"Get Seo Fix Pack","description":"SPENDS NOTHING. The pack for one fix: its instructions, any generated files, and AGENTS.md / CLAUDE.md.\n\n404 for a fix this organisation does not have.","operationId":"get_seo_fix_pack_seo_fixes__fix_id__pack_get","parameters":[{"name":"fix_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"A fix id from `GET /seo/fixes`.","title":"Fix Id"},"description":"A fix id from `GET /seo/fixes`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoAgentFixPack_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/seo/fixes/{fix_id}/claim":{"post":{"tags":["SEO"],"summary":"Claim Seo Fix","description":"SPENDS NOTHING. Claim one queued fix for your coding agent.\n\nRow-locked: if another agent already holds it the answer is 409. Claiming again with the same `agent` label\nis a no-op. A claim nobody completes expires after a few hours and the fix is offered again.","operationId":"claim_seo_fix_seo_fixes__fix_id__claim_post","parameters":[{"name":"fix_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"A fix id from `GET /seo/fixes`.","title":"Fix Id"},"description":"A fix id from `GET /seo/fixes`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SeoClaimFixRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoClaimFixResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"intent:write","x-graph8-lifecycle":"active"}},"/seo/fixes/{fix_id}/complete":{"post":{"tags":["SEO"],"summary":"Complete Seo Fix","description":"SPENDS NOTHING. Report a claimed fix as done (with the commit or pull request) or as failed (with why).\n\n`outcome=done` needs `ref`, a commit SHA or an http(s) URL, and moves the fix to `applied`; graph8 then\nre-fetches the live page to verify it. `outcome=failed` needs `note`. 409 when the fix is not claimed by\nthis agent, 422 for a missing or malformed `ref`.","operationId":"complete_seo_fix_seo_fixes__fix_id__complete_post","parameters":[{"name":"fix_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"A fix id from `GET /seo/fixes`.","title":"Fix Id"},"description":"A fix id from `GET /seo/fixes`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SeoCompleteFixRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoCompleteFixResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"intent:write","x-graph8-lifecycle":"active"}},"/seo/today":{"get":{"tags":["SEO"],"summary":"Get Seo Today","description":"SPENDS NOTHING. Today in Signals > SEO: health, KPIs, what changed, the approval queue and open alerts.\n\nEvery modelled number carries `confidence` (`measured`, `estimated` or `partial`). Sources that are not\nconnected degrade to a card saying so; `sources` lists which answered.","operationId":"get_seo_today_seo_today_get","parameters":[{"name":"domain","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"description":"A tracked domain. Omit for the primary one.","title":"Domain"},"description":"A tracked domain. Omit for the primary one."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoToday_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/seo/pages/360":{"get":{"tags":["SEO"],"summary":"List Seo Pages 360","description":"SPENDS NOTHING. The Page360 grid: every page with Search Console, vitals, visitors, companies and open fixes.\n\n`filter=money` keeps pages that sit on a closed-won or open-deal path (an inference, labelled estimated).\n`gsc_connected` is false until Search Console is linked; the rows then carry visitor data only.","operationId":"list_seo_pages_360_seo_pages_360_get","parameters":[{"name":"domain","in":"query","required":true,"schema":{"type":"string","maxLength":255,"description":"A tracked domain.","title":"Domain"},"description":"A tracked domain."},{"name":"q","in":"query","required":false,"schema":{"type":"string","maxLength":200,"description":"Only pages whose path contains this text.","default":"","title":"Q"},"description":"Only pages whose path contains this text."},{"name":"sort","in":"query","required":false,"schema":{"enum":["pageviews","clicks","position","companies","pipeline","issues"],"type":"string","default":"pageviews","title":"Sort"}},{"name":"order","in":"query","required":false,"schema":{"enum":["asc","desc"],"type":"string","default":"desc","title":"Order"}},{"name":"filter","in":"query","required":false,"schema":{"enum":["all","money","decay","fixes","companies","slow"],"type":"string","default":"all","title":"Filter"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Rows to return.","default":50,"title":"Limit"},"description":"Rows to return."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Rows to skip.","default":0,"title":"Offset"},"description":"Rows to skip."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoPages360_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/seo/pages/360/detail":{"get":{"tags":["SEO"],"summary":"Get Seo Page 360","description":"SPENDS NOTHING. One page in full: Search Console, vitals, indexing, visitors, companies, top queries, open fixes.\n\n404 when the page has not been analysed yet.","operationId":"get_seo_page_360_seo_pages_360_detail_get","parameters":[{"name":"domain","in":"query","required":true,"schema":{"type":"string","maxLength":255,"description":"A tracked domain.","title":"Domain"},"description":"A tracked domain."},{"name":"url","in":"query","required":true,"schema":{"type":"string","maxLength":2000,"description":"The page URL or path, e.g. /pricing.","title":"Url"},"description":"The page URL or path, e.g. /pricing."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SeoPage360_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/radar/overview":{"get":{"tags":["Radar"],"summary":"Overview","description":"Radar dashboard summary: tracked counts, 7-day moves, the threat board,\nrecent moves, pipeline funnel, and derived alerts.","operationId":"overview_radar_overview_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/competitors":{"get":{"tags":["Radar"],"summary":"List Competitors","description":"Every tracked competitor profile (active + inactive), tier then domain.","operationId":"list_competitors_radar_competitors_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"},"post":{"tags":["Radar"],"summary":"Create Competitor","description":"Add one competitor to track. 409 if already tracked, 422 at the cap.","operationId":"create_competitor_radar_competitors_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateCompetitorRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"radar:write","x-graph8-lifecycle":"active"}},"/radar/competitors/bulk":{"post":{"tags":["Radar"],"summary":"Bulk Add Competitors","description":"Add many competitors at once (normalize + dedup + 20-competitor cap).","operationId":"bulk_add_competitors_radar_competitors_bulk_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BulkCompetitorsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"radar:write","x-graph8-lifecycle":"active"}},"/radar/competitors/suggestions":{"get":{"tags":["Radar"],"summary":"Competitor Suggestions","description":"Detected-but-untracked competitors from intelligence + global docs.","operationId":"competitor_suggestions_radar_competitors_suggestions_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/competitors/{competitor_id}":{"get":{"tags":["Radar"],"summary":"Get Competitor","description":"Single-competitor aggregation: profile + pages-tracked + recent changes + gaps.","operationId":"get_competitor_radar_competitors__competitor_id__get","parameters":[{"name":"competitor_id","in":"path","required":true,"schema":{"type":"string","title":"Competitor Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Radar"],"summary":"Update Competitor","description":"Update a competitor profile (tier, active flag, name, or scan_config).","operationId":"update_competitor_radar_competitors__competitor_id__patch","parameters":[{"name":"competitor_id","in":"path","required":true,"schema":{"type":"string","title":"Competitor Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PatchCompetitorRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"radar:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Radar"],"summary":"Delete Competitor","description":"Deactivate a tracked competitor while retaining its evidence history.","operationId":"delete_competitor_radar_competitors__competitor_id__delete","parameters":[{"name":"competitor_id","in":"path","required":true,"schema":{"type":"string","title":"Competitor Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"radar:delete","x-graph8-lifecycle":"active"}},"/radar/competitors/{competitor_id}/pages":{"get":{"tags":["Radar"],"summary":"Get Competitor Pages","description":"Distinct tracked pages for one competitor (latest snapshot per URL).","operationId":"get_competitor_pages_radar_competitors__competitor_id__pages_get","parameters":[{"name":"competitor_id","in":"path","required":true,"schema":{"type":"string","title":"Competitor Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/competitors/{competitor_id}/ads":{"get":{"tags":["Radar"],"summary":"Get Competitor Ads","description":"Captured ad creatives for one competitor (durable snapshot corpus).","operationId":"get_competitor_ads_radar_competitors__competitor_id__ads_get","parameters":[{"name":"competitor_id","in":"path","required":true,"schema":{"type":"string","title":"Competitor Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/competitors/{competitor_id}/traffic":{"get":{"tags":["Radar"],"summary":"Get Competitor Traffic","description":"Traffic detail for one competitor: current estimate + trend + ETV history.","operationId":"get_competitor_traffic_radar_competitors__competitor_id__traffic_get","parameters":[{"name":"competitor_id","in":"path","required":true,"schema":{"type":"string","title":"Competitor Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/competitors/{competitor_id}/posts":{"get":{"tags":["Radar"],"summary":"Get Competitor Posts","description":"LinkedIn posts for one competitor (listener store, then corpus fallback).","operationId":"get_competitor_posts_radar_competitors__competitor_id__posts_get","parameters":[{"name":"competitor_id","in":"path","required":true,"schema":{"type":"string","title":"Competitor Id"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/competitors/{competitor_id}/engagers":{"get":{"tags":["Radar"],"summary":"Get Competitor Engagers","description":"Steal-Their-Audience: known-to-us people who engage this rival's content.\n\nThe cb function declares a deals-read permission dependency; here we pass a\nsynthesized org-admin principal (``_=True``) so the gate is satisfied at the\npublic surface (RBAC specs out of scope by decision).","operationId":"get_competitor_engagers_radar_competitors__competitor_id__engagers_get","parameters":[{"name":"competitor_id","in":"path","required":true,"schema":{"type":"string","title":"Competitor Id"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":100,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/competitors/{competitor_id}/battle-card":{"get":{"tags":["Radar"],"summary":"Competitor Battle Card","description":"Sales-enablement battle card composed from existing Radar intel (no LLM).","operationId":"competitor_battle_card_radar_competitors__competitor_id__battle_card_get","parameters":[{"name":"competitor_id","in":"path","required":true,"schema":{"type":"string","title":"Competitor Id"}},{"name":"include_unverified","in":"query","required":false,"schema":{"type":"boolean","description":"Also list unverified (hypothesis) advantages. By default only claims backed by proof-catalog evidence are shown, the same as the app.","default":false,"title":"Include Unverified"},"description":"Also list unverified (hypothesis) advantages. By default only claims backed by proof-catalog evidence are shown, the same as the app."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/competitors/{competitor_id}/discover-pages":{"get":{"tags":["Radar"],"summary":"Discover Competitor Pages","description":"Discover a competitor's pages (Firecrawl /map) for the tracked-pages picker.","operationId":"discover_competitor_pages_radar_competitors__competitor_id__discover_pages_get","parameters":[{"name":"competitor_id","in":"path","required":true,"schema":{"type":"string","title":"Competitor Id"}},{"name":"refresh","in":"query","required":false,"schema":{"type":"boolean","description":"Bypass the cached page inventory and re-map the site (paid).","default":false,"title":"Refresh"},"description":"Bypass the cached page inventory and re-map the site (paid)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"radar:run","x-graph8-lifecycle":"active"}},"/radar/competitors/{competitor_id}/scan":{"post":{"tags":["Radar"],"summary":"Scan Competitor","description":"BILLABLE: enqueue a fresh scan of one competitor (Celery). Returns {task_id}.","operationId":"scan_competitor_radar_competitors__competitor_id__scan_post","parameters":[{"name":"competitor_id","in":"path","required":true,"schema":{"type":"string","title":"Competitor Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"radar:run","x-graph8-lifecycle":"active"}},"/radar/scan-all":{"post":{"tags":["Radar"],"summary":"Scan All Competitors","description":"BILLABLE: enqueue a scan for every active competitor (Celery).","operationId":"scan_all_competitors_radar_scan_all_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"radar:run","x-graph8-lifecycle":"active"}},"/radar/gaps":{"get":{"tags":["Radar"],"summary":"List Gaps","description":"List competitive gaps, optionally filtered by lens / status / competitor.","operationId":"list_gaps_radar_gaps_get","parameters":[{"name":"lens","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Lens"}},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"}},{"name":"competitor_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Competitor Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/gaps/{gap_id}":{"patch":{"tags":["Radar"],"summary":"Update Gap","description":"Update a gap's status (open / dismissed / converted).","operationId":"update_gap_radar_gaps__gap_id__patch","parameters":[{"name":"gap_id","in":"path","required":true,"schema":{"type":"string","title":"Gap Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PatchGapRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"radar:write","x-graph8-lifecycle":"active"}},"/radar/gaps/analyze":{"post":{"tags":["Radar"],"summary":"Analyze Gaps","description":"BILLABLE: enqueue gap analysis across the tracked set (LLM, Celery).","operationId":"analyze_gaps_radar_gaps_analyze_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyzeGapsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"radar:run","x-graph8-lifecycle":"active"}},"/radar/opportunities":{"get":{"tags":["Radar"],"summary":"List Opportunities","description":"List opportunities - the scored OPEN gaps, optionally filtered by lane.","operationId":"list_opportunities_radar_opportunities_get","parameters":[{"name":"lane","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Lane"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/opportunities/{gap_id}/approve":{"post":{"tags":["Radar"],"summary":"Approve Opportunity","description":"Approve one scored opportunity - converts it into an initiative + stubs.","operationId":"approve_opportunity_radar_opportunities__gap_id__approve_post","parameters":[{"name":"gap_id","in":"path","required":true,"schema":{"type":"string","title":"Gap Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApproveOpportunityRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"radar:write","x-graph8-lifecycle":"active"}},"/radar/opportunities/approve-all":{"post":{"tags":["Radar"],"summary":"Approve All Opportunities","description":"Bulk-approve opportunities in one lane - currently FAIL-CLOSED (HTTP 409).\n\ncampaign_builder deliberately rejects bulk approval until an item-by-item\nreview contract exists: ``approve_all_opportunities`` raises 409 'Bulk\napproval requires review' on every call (campaign_builder/routers/radar.py).\nThis bridge forwards to that handler so the 409 is surfaced honestly instead\nof fabricating a 200 - it never mutates or bills. Approve opportunities one\nat a time via ``POST /radar/opportunities/{gap_id}/approve``.\n\nProduct gap (out of this bridge's scope): the developer-api reference\n(docs/developer-api-reference.md ~L3799-3800) and the MCP tool\ng8_radar_approve_all_opportunities still advertise a working 'top-50 drain'\nand must be re-documented to the 409 contract, or the cb handler must gain a\nreal bulk-review flow.","operationId":"approve_all_opportunities_radar_opportunities_approve_all_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApproveAllRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"radar:write","x-graph8-lifecycle":"active"}},"/radar/initiatives":{"get":{"tags":["Radar"],"summary":"List Initiatives","description":"List radar initiatives (converted opportunities under execution).","operationId":"list_initiatives_radar_initiatives_get","parameters":[{"name":"lane","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Lane"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/initiatives/measure":{"post":{"tags":["Radar"],"summary":"Measure Initiatives","description":"Run the performance loopback now (free, DB-only). Returns {measured}.\n\nThe cb function declares a settings:write dependency; we pass _=None so the\ngate is satisfied at the public surface (RBAC specs out of scope).","operationId":"measure_initiatives_radar_initiatives_measure_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"radar:run","x-graph8-lifecycle":"active"}},"/radar/optimization-runs":{"get":{"tags":["Radar"],"summary":"Optimization Runs","description":"Radar-spawned content-refresh grids with lean score aggregates.","operationId":"optimization_runs_radar_optimization_runs_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/aeo":{"get":{"tags":["Radar"],"summary":"Aeo Overview","description":"Answer-engine share-of-voice: mention/citation rate, SoV, leaderboard.\n\n``engine`` is passed through as a RESOLVED value. Called directly (not via\nFastAPI), an omitted param would keep its ``Query(default=None)`` sentinel,\nwhich the cb handler reads as a truthy unsupported engine and rejects with a\n400 on every call - so the value must be forwarded explicitly.","operationId":"aeo_overview_radar_aeo_get","parameters":[{"name":"engine","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter to one answer engine (e.g. claude, perplexity).","title":"Engine"},"description":"Filter to one answer engine (e.g. claude, perplexity)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/aeo/probes":{"get":{"tags":["Radar"],"summary":"Aeo Probes","description":"List the org's tracked AEO buyer-intent probes.","operationId":"aeo_probes_radar_aeo_probes_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/aeo/run":{"post":{"tags":["Radar"],"summary":"Aeo Run","description":"BILLABLE: trigger an AEO run (one paid LLM call per probe, Celery).\n\nThe cb function declares a settings:write dependency; we pass _=None so the\ngate is satisfied at the public surface (RBAC specs out of scope).","operationId":"aeo_run_radar_aeo_run_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"radar:run","x-graph8-lifecycle":"active"}},"/radar/snapshots/{snapshot_id}/compare":{"get":{"tags":["Radar"],"summary":"Compare Snapshot","description":"Before/after diff for one page snapshot (vs prior capture or `against`).","operationId":"compare_snapshot_radar_snapshots__snapshot_id__compare_get","parameters":[{"name":"snapshot_id","in":"path","required":true,"schema":{"type":"string","title":"Snapshot Id"}},{"name":"against","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Against"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/monitoring/content":{"get":{"tags":["Radar"],"summary":"Monitoring Content","description":"Competitor content-change feed with the same filters as the cb route.","operationId":"monitoring_content_radar_monitoring_content_get","parameters":[{"name":"competitor_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Competitor Id"}},{"name":"kind","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Kind"}},{"name":"change_category","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Change Category"}},{"name":"change_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Change Type"}},{"name":"min_significance","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","maximum":100,"minimum":0},{"type":"null"}],"title":"Min Significance"}},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Date From"}},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Date To"}},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Search"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/monitoring/page-history":{"get":{"tags":["Radar"],"summary":"Page History","description":"Full capture history for one page (competitor + url), newest-first.","operationId":"page_history_radar_monitoring_page_history_get","parameters":[{"name":"url","in":"query","required":true,"schema":{"type":"string","maxLength":2048,"title":"Url"}},{"name":"competitor_id","in":"query","required":true,"schema":{"type":"string","title":"Competitor Id"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"default":20,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/monitoring/linkedin":{"get":{"tags":["Radar"],"summary":"Monitoring Linkedin","description":"Competitor LinkedIn posts (listener store first, then corpus fallback).\n\nEvery filter is forwarded as a RESOLVED value. Called directly (not via\nFastAPI), omitted ``date_from``/``date_to`` params would keep their\n``Query`` sentinels, and the cb handler's ``date_from > date_to`` guard then\nraises ``TypeError`` (Query vs Query) -> a 500 on every call. Passing the\ncoerced ``date``/``None`` values instead lets the guard emit a clean 422 on\nan inverted range and exposes the page/domain/date filters the cb route\nsupports.","operationId":"monitoring_linkedin_radar_monitoring_linkedin_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","maximum":1000,"minimum":1,"default":1,"title":"Page"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"competitor_domain","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Competitor Domain"}},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"Date From"}},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"Date To"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/monitoring/ads":{"get":{"tags":["Radar"],"summary":"Monitoring Ads","description":"Ads & keywords: durable ad_creative corpus + persisted organic/paid keywords.","operationId":"monitoring_ads_radar_monitoring_ads_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:run","x-graph8-lifecycle":"active"}},"/radar/monitoring/ads/{ad_id}":{"get":{"tags":["Radar"],"summary":"Monitoring Ad Detail","description":"One ad's full detail (copy / headline / image / dates) + rival context.","operationId":"monitoring_ad_detail_radar_monitoring_ads__ad_id__get","parameters":[{"name":"ad_id","in":"path","required":true,"schema":{"type":"string","maxLength":256,"title":"Ad Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/keyword-gap":{"get":{"tags":["Radar"],"summary":"Keyword Gap","description":"Keywords each rival ranks for that the org does NOT (\"what you're missing\").","operationId":"keyword_gap_radar_keyword_gap_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:run","x-graph8-lifecycle":"active"}},"/radar/feature-matrix":{"get":{"tags":["Radar"],"summary":"Feature Matrix","description":"Capability/feature comparison matrix across the tracked competitor set.","operationId":"feature_matrix_radar_feature_matrix_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/traffic":{"get":{"tags":["Radar"],"summary":"Traffic","description":"Traffic & market view: per-competitor visit estimates + trend (self marked).","operationId":"traffic_radar_traffic_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/own-traffic-estimate":{"get":{"tags":["Radar"],"summary":"Own Traffic Estimate","description":"Estimated own-domain traffic (DataForSEO) - Traffic & market fallback.","operationId":"own_traffic_estimate_radar_own_traffic_estimate_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:run","x-graph8-lifecycle":"active"}},"/radar/alerts/dispatch":{"post":{"tags":["Radar"],"summary":"Dispatch Alerts","description":"Detect + deliver new competitor-move alerts now. Returns {delivered}.\n\nThe cb function declares a settings:write dependency; we pass _=None so the\ngate is satisfied at the public surface (RBAC specs out of scope).","operationId":"dispatch_alerts_radar_alerts_dispatch_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"radar:run","x-graph8-lifecycle":"active"}},"/radar/settings":{"get":{"tags":["Radar"],"summary":"Get Settings","description":"Read the org's Radar settings (cadence, alert toggles, channels, ad_source).","operationId":"get_settings_radar_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"},"put":{"tags":["Radar"],"summary":"Put Settings","description":"Replace the org's Radar settings (full object).","operationId":"put_settings_radar_settings_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RadarSettings"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"radar:write","x-graph8-lifecycle":"active"}},"/radar/initiatives/{initiative_id}":{"patch":{"tags":["Radar"],"summary":"Update Initiative","description":"Change an initiative's owner and/or due date after approval.\n\nPartial update: an omitted field is left alone, `owner_id: null` unassigns. The owner must be a member of this\norganization (400 otherwise). `create_crm_task: true` also opens a CRM task for the resolved owner and needs a\ntask-write permission; the task is a best-effort side effect that never fails the edit, and `crm_task_id` is null\nwhen none was made. 404 for an initiative that is not this organization's.","operationId":"update_initiative_radar_initiatives__initiative_id__patch","parameters":[{"name":"initiative_id","in":"path","required":true,"schema":{"type":"string","description":"Initiative id (from GET /radar/initiatives).","title":"Initiative Id"},"description":"Initiative id (from GET /radar/initiatives)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PatchInitiativeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"radar:write","x-graph8-lifecycle":"active"}},"/radar/settings/credit-usage":{"get":{"tags":["Radar"],"summary":"Get Credit Usage","description":"This month's Radar scan-credit usage against the effective cap, with a run-rate projection to month end.\n\n`used_this_month`, `cap`, `cap_is_default` (true when the organization has not set its own cap) and\n`projected_month_end`. Reads only; a scan is what spends.","operationId":"get_credit_usage_radar_settings_credit_usage_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/competitors/{competitor_id}/battle-intel":{"get":{"tags":["Radar"],"summary":"Get Battle Intel","description":"The revenue this rival affects: win rate (and the organization baseline), open pipeline at risk, lost revenue.\n\nAggregated from the deals the KEY may see, so two keys can read different numbers. `win_rate` and\n`baseline_win_rate` are null (never a percentage) below a minimum closed-deal sample or with no closed deals. The\nconfirmed and suggested counts always ride with the dollar totals. No model call, no external call. 404 for an\nunknown competitor.","operationId":"get_battle_intel_radar_competitors__competitor_id__battle_intel_get","parameters":[{"name":"competitor_id","in":"path","required":true,"schema":{"type":"string","description":"Competitor id (from GET /radar/competitors).","title":"Competitor Id"},"description":"Competitor id (from GET /radar/competitors)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/competitive-pipeline":{"get":{"tags":["Radar"],"summary":"Get Competitive Pipeline","description":"Every tracked rival's win/loss and revenue at risk in one read, with the organization's overall win rate.\n\nThe same per-rival fields as `battle-intel`, over the deals the KEY may see, without a call per rival.","operationId":"get_competitive_pipeline_radar_competitive_pipeline_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/competitors/{competitor_id}/hiring":{"get":{"tags":["Radar"],"summary":"Get Competitor Hiring","description":"The last computed hiring-spike snapshot for one rival.\n\n`available: true` with `postings_7d`, `baseline_weekly_avg`, `multiple` and `weekly_series` while the rival is\nspiking; otherwise `{available: false, reason}`: not spiking (the common case), no sweep has run yet, or the cache\nis unreachable. It never computes anything fresh. 404 for an unknown competitor.","operationId":"get_competitor_hiring_radar_competitors__competitor_id__hiring_get","parameters":[{"name":"competitor_id","in":"path","required":true,"schema":{"type":"string","description":"Competitor id (from GET /radar/competitors).","title":"Competitor Id"},"description":"Competitor id (from GET /radar/competitors)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/radar/competitors/{competitor_id}/engagers/activate":{"post":{"tags":["Radar"],"summary":"Activate Engagers","description":"Add a rival's known engagers to an existing list, or enroll them in a LIVE or WAITING sequence.\n\n`enroll_sequence` adds them to the sequence's bound list and syncs at once, so they can be contacted by that\nsequence: it needs the sequence-write scope as well. Every contact id is checked against the rival's current\nengager set (404 naming the strangers, nothing added). The app's list-write, contact-write and rep-limit checks all\nrun: a rep-limit conflict answers 409 `CONFLICT_REVIEW_REQUIRED` and is resubmitted with `conflict_resolution`\n(and `include_warned_ids`), exactly as in the app. Preview first with `.../activate/preview`.","operationId":"activate_engagers_radar_competitors__competitor_id__engagers_activate_post","parameters":[{"name":"competitor_id","in":"path","required":true,"schema":{"type":"string","description":"Competitor id (from GET /radar/competitors).","title":"Competitor Id"},"description":"Competitor id (from GET /radar/competitors)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ActivateEngagersRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"radar:run","x-graph8-lifecycle":"active"}},"/radar/competitors/{competitor_id}/engagers/activate/preview":{"post":{"tags":["Radar"],"summary":"Preview Activate Engagers","description":"Dry run of the activation: what would be added and why the rest would be skipped. WRITES NOTHING.\n\n`will_add`, and `skipped` split into `suppressed` (sequence enrollment only), `already_member`, `conflicts`\n(blocked by a rep limit), `warned` (409 on the real call; resubmit with `conflict_resolution`) and `not_engager`.\nThe access checks still fail (403 or 404) exactly as the real call does.","operationId":"preview_activate_engagers_radar_competitors__competitor_id__engagers_activate_preview_post","parameters":[{"name":"competitor_id","in":"path","required":true,"schema":{"type":"string","description":"Competitor id (from GET /radar/competitors).","title":"Competitor Id"},"description":"Competitor id (from GET /radar/competitors)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ActivateEngagersRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"radar:read","x-graph8-lifecycle":"active"}},"/opensearch/search":{"post":{"tags":["OpenSearch"],"summary":"Opensearch Search","description":"Structured search across one of the whitelisted mashup OpenSearch indices.\n\nUse this when the LLM needs to look up enriched person / company records\nby attribute (domain, industry, country, hem). For the hot HEM-or-IP\nresolve path, prefer ``/opensearch/resolve`` — it's a single round trip\nand friendlier to cache. Contact/company mashup searches automatically\napply the authenticated organization's deliverability protection policy.","operationId":"opensearch_search_opensearch_search_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OpenSearchSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OpenSearchSearchResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"search:write","x-graph8-lifecycle":"active"}},"/opensearch/resolve":{"post":{"tags":["OpenSearch"],"summary":"Opensearch Resolve","description":"Bulk HEM -> CONTACT_ID or IP -> COMPANY_ID resolution.\n\nBacked by the existing ``MashupService`` which already batches the OpenSearch\nrequest in chunks of 10k. Returns a dense ``{input: matched_id | null}``\nmapping so the caller can iterate the inputs without re-querying for misses.","operationId":"opensearch_resolve_opensearch_resolve_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OpenSearchResolveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OpenSearchResolveResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"search:write","x-graph8-lifecycle":"active"}},"/opensearch/count":{"post":{"tags":["OpenSearch"],"summary":"Opensearch Count","description":"Exact match count for one of the whitelisted mashup indices.\n\nSame ``index`` + ``filters`` shape as ``/opensearch/search`` but returns\nonly the count via the native OpenSearch ``_count`` API, so it is NOT\ncapped at the 10000 ``track_total_hits`` ceiling that ``/search``'s\n``total`` saturates at. This is the right call for TAM cell-sizing.\n\nNote: ``mashup_companies`` and ``mashup_contacts`` are the same physical,\ncontact-grained index — a count over ``mashup_companies`` counts contact\nrows, not unique companies. For a unique-company total use\n``/opensearch/aggregate`` with ``uniqExact`` on ``COMPANY_ID``. Mashup\ncounts automatically apply the organization's deliverability policy.","operationId":"opensearch_count_opensearch_count_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OpenSearchCountRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OpenSearchCountResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"search:write","x-graph8-lifecycle":"active"}},"/opensearch/aggregate":{"post":{"tags":["OpenSearch"],"summary":"Opensearch Aggregate","description":"Generic, allowlist-bounded GROUP BY over a whitelisted mashup index.\n\nTranslates ``group_by`` into nested OpenSearch ``terms`` aggregations with\nmetric sub-aggs, then applies ``having`` / ``sort`` / ``limit`` to the\nflattened groups. This is the matrix-walk primitive for TAM design (e.g.\ncount companies by NAICS x state x employee band in one call).\n\nGuardrails: group_by depth is capped at 3, per-level bucket size tapers by\ndepth (``_AGG_TERMS_SIZE_BY_DEPTH``), the agg list is capped at 10, and\nreturned groups at ``limit`` (<=1000). Counts from ``terms`` /\n``cardinality`` are APPROXIMATE on a sharded index. Since\n``mashup_companies``/``mashup_contacts`` share one contact-grained index,\nuse ``uniqExact`` on ``COMPANY_ID`` for true unique-company counts. Mashup\naggregations automatically apply the organization's deliverability policy.","operationId":"opensearch_aggregate_opensearch_aggregate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OpenSearchAggregateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OpenSearchAggregateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"search:write","x-graph8-lifecycle":"active"}},"/clickhouse/mashup":{"post":{"tags":["ClickHouse"],"summary":"Clickhouse Mashup","description":"Enrich UP_IDs / HEMs / domains against the ClickHouse Cloud mashup tables.\n\nUse this for bulk enrichment workflows where the agent already has a\nprimary key (UP_ID from ``g8_opensearch_resolve_ids``, a HEM from a\nvisitor row, or a company domain from CRM). For free-form attribute\nsearch prefer ``g8_opensearch_search`` against ``mashup_contacts``.","operationId":"clickhouse_mashup_clickhouse_mashup_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ClickhouseMashupRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ClickhouseMashupResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"search:write","x-graph8-lifecycle":"active"}},"/clickhouse/org-analytics":{"post":{"tags":["ClickHouse"],"summary":"Clickhouse Org Analytics","description":"Per-org visitor + intent analytics from ch3.\n\nThe database name is always derived from the authenticated user's\n``organization.id`` (lower-cased) — the request body never carries\nan org_id. The agent cannot reach another org's data even if it\ntries.","operationId":"clickhouse_org_analytics_clickhouse_org_analytics_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ClickhouseOrgAnalyticsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ClickhouseOrgAnalyticsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"search:write","x-graph8-lifecycle":"active"}},"/events":{"get":{"tags":["Events"],"summary":"List Org Events","description":"List the organisation's events, newest first, with cursor pagination.\n\nCovers every event the EDA pipeline stores for the org plus website tracking\nrows. Filters combine with AND. Pages are stable under concurrent writes:\nthe cursor encodes the last (timestamp, uid) seen.","operationId":"list_org_events_events_get","parameters":[{"name":"type","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"string"}},{"type":"null"}],"description":"Filter by event type (repeatable), e.g. sequencer, inbox, voiceai.","title":"Type"},"description":"Filter by event type (repeatable), e.g. sequencer, inbox, voiceai."},{"name":"name","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"string"}},{"type":"null"}],"description":"Filter by event name (repeatable), e.g. sequence_email_replied.","title":"Name"},"description":"Filter by event name (repeatable), e.g. sequence_email_replied."},{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"description":"Filter by producing service.","title":"Source"},"description":"Filter by producing service."},{"name":"contact_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"description":"Only events whose message.contact_id matches.","title":"Contact Id"},"description":"Only events whose message.contact_id matches."},{"name":"sequence_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"description":"Only events whose message.sequence_id matches.","title":"Sequence Id"},"description":"Only events whose message.sequence_id matches."},{"name":"campaign_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"description":"Only events whose message.campaign_id matches.","title":"Campaign Id"},"description":"Only events whose message.campaign_id matches."},{"name":"since","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"description":"Window start (ISO 8601). Defaults to 7 days before `until`.","title":"Since"},"description":"Window start (ISO 8601). Defaults to 7 days before `until`."},{"name":"until","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"description":"Window end, exclusive (ISO 8601). Defaults to now.","title":"Until"},"description":"Window end, exclusive (ISO 8601). Defaults to now."},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":512},{"type":"null"}],"description":"`next_cursor` from the previous page.","title":"Cursor"},"description":"`next_cursor` from the previous page."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Page size.","default":50,"title":"Limit"},"description":"Page size."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgEventFeedPage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/phone-numbers/purchase":{"post":{"tags":["Phone Numbers"],"summary":"Buy a phone number","description":"Buy a number from Twilio or Telnyx. THIS SPENDS CREDITS AND REAL MONEY.\n\nCharged on PURCHASE, not on first use: the handler holds credits, buys the\nnumber from the carrier, stores it, registers it with the voice platform\nand only then converts the hold to a charge. A number bought and never\ndialled has still cost.\n\nNot idempotent by number - buy the same number twice and the second call\nis a 409 rather than a second charge, but a retry after a timeout you\ncannot see the outcome of may have already succeeded. Send an\n`Idempotency-Key` header; every POST on this API honours it.\n\n`402` means insufficient credits and is the one failure worth handling\ndistinctly - the number was not bought and nothing was charged.","operationId":"purchase_phone_number_phone_numbers_purchase_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PurchasePhoneRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PhoneNumberPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/phone-numbers/release":{"post":{"tags":["Phone Numbers"],"summary":"Release a phone number","description":"Give a number back to the carrier. IRREVERSIBLE.\n\nThe number returns to the provider's pool and can be bought by anyone,\nincluding a competitor. Inbound calls and messages to it stop reaching\nthis organisation immediately; there is no grace period and no undo.\n\nOrder matters and is not transactional: the carrier release happens first,\nthen voice deregistration (best-effort), then the local record. A failure\nafter the carrier release leaves the number gone but the record behind -\nwhich is why this returns the outcome rather than a bare 204.","operationId":"release_phone_number_phone_numbers_release_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ReleasePhoneRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PhoneNumberPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/phone-numbers/update-assignee":{"patch":{"tags":["Phone Numbers"],"summary":"Reassign a phone number","description":"Move a number to a different person, and tell voice about it.\n\nNot a label: the assignee drives inbound ring targeting, missed-call\nnotification and which numbers appear in that person's outbound caller-ID\nrotation pool.\n\nADMIN-ONLY through this API. The app also accepts the number's current\nassignee or its creator, but an API key is an ORGANISATION credential with\nno `user_id`, so it can never be either - leaving it to fall through to the\nrole check is what made this route 403 for every key before the role was\nsupplied.","operationId":"update_phone_assignee_phone_numbers_update_assignee_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateAssigneeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PhoneNumberPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/phone-numbers/update-capabilities":{"patch":{"tags":["Phone Numbers"],"summary":"Switch a number between dialer and voice AI","description":"Change what a number is for, and re-provision it to match.\n\nThis reaches the voice platform: the LiveKit trunks and the carrier\n`voice_url` are re-pointed so inbound calls arrive where the new capability\nsays they should. A number is briefly answering neither while that happens.\n\nThe two flags are not independent. `dialer` set with `voice` unset means\ndialer; every other combination means voice AI - which is the app's own\nderivation, mirrored rather than reinvented.\n\nAdmin-only for the same reason as `update-assignee`.","operationId":"update_phone_capabilities_phone_numbers_update_capabilities_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateCapabilitiesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PhoneNumberPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/phone-numbers/a2p/inputs":{"post":{"tags":["Phone Numbers"],"summary":"Save A2P brand and campaign details","description":"Save the brand and campaign details WITHOUT submitting them.\n\nNothing reaches a carrier and nothing is charged. This is the draft step -\ncall it as often as you like, then submit once with `/a2p/register`.\n\nThe save REPLACES what was there rather than merging, so send the whole\nobject each time.","operationId":"save_a2p_inputs_phone_numbers_a2p_inputs_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/A2pRegisterRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PhoneNumberPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/phone-numbers/a2p/register":{"post":{"tags":["Phone Numbers"],"summary":"Submit A2P 10DLC registration","description":"Submit the organisation to the US carrier registry. THIS REACHES A\nTHIRD PARTY AND CARRIES CARRIER FEES.\n\nSaves the inputs, then starts a durable registration saga and returns its\n`workflow_id` immediately - registration takes days, not seconds, and the\ncarriers can reject it. Without an approved registration, US carriers\nfilter application-to-person SMS from these numbers, so this is not\noptional for messaging.\n\nIDEMPOTENT PER ORGANISATION: the workflow id is derived from the org, so a\nsecond call while one is running is a no-op rather than a second\nsubmission. Call `/a2p/inputs` first if you only want to save a draft.","operationId":"start_a2p_registration_phone_numbers_a2p_register_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/A2pRegisterRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PhoneNumberPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/phone-numbers/a2p/reconcile":{"post":{"tags":["Phone Numbers"],"summary":"Re-run A2P registration for stuck numbers","description":"Re-attach this organisation's pending or failed numbers to its A2P\nmessaging service.\n\nThe repair step, not the registration step. A worker already does this\nevery six hours; this is how to stop waiting for it after fixing whatever\nmade a number fail. It re-runs against numbers whose status is pending or\nfailed and leaves registered ones alone, so it is safe to call repeatedly.\n\nTiered as an ordinary write rather than a spend: it reconciles state the\n`/a2p/register` submission already paid for and starts no new registration.\n\n`503` means the messaging service is not configured for this environment,\nwhich is a deployment fact rather than anything the caller did wrong.","operationId":"reconcile_a2p_registration_phone_numbers_a2p_reconcile_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PhoneNumberPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/numbers/provision":{"post":{"tags":["Phone Numbers"],"summary":"Register a number with the voice platform","description":"Wire an already-owned number into the voice platform.\n\nBUYS NOTHING. Voice calls this operation `purchase` and it is published\nhere as `provision` deliberately: it creates SIP trunks and dispatch rules\nfor a number you already hold, while `POST /phone-numbers/purchase` is the\none that spends credits and buys a DID. Two operations both called\n\"purchase\", one of which takes money and one of which does not, is not a\ndistinction to leave to a docstring.\n\nIDEMPOTENT: a number already registered comes back as success rather than\nan error, and an unverified Telnyx number has its caller-ID verification\nre-queued on the way through.\n\nReach for this to repair a purchase whose voice half failed, or to adopt a\nnumber bought outside graph8. `org_id` is taken from the API key.","operationId":"provision_voice_number_voice_numbers_provision_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VoiceNumberProvisionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PhoneNumberPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/numbers":{"delete":{"tags":["Phone Numbers"],"summary":"Deregister a number from the voice platform","description":"Tear down a number's SIP trunks, dispatch rules and carrier routing.\n\nDOES NOT RELEASE THE NUMBER. The organisation still owns it and is still\nbilled for it by the carrier - it simply stops being answerable. To give it\nback, use `POST /phone-numbers/release`, which does this and the carrier\nrelease and the local record.\n\nVoice's own handler identifies the number by value with no tenant check, so\nthis route first asserts the caller's organisation owns it. A number that\nexists in voice but was never recorded against this organisation is a 404.","operationId":"delete_voice_number_voice_numbers_delete","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VoiceNumberDeleteRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PhoneNumberPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/numbers/verify-caller-id/{phone_number}":{"post":{"tags":["Phone Numbers"],"summary":"Verify a Telnyx number as a caller ID","description":"Start caller-ID verification for a Telnyx number.\n\nONLY Telnyx numbers need this, and asking for a Twilio one is a 400 rather\nthan a silent success - Twilio DIDs are valid callers by construction and\nhave no verification record at all.\n\nVerification takes minutes, so this returns immediately with either\n`already_verified` or `verification_started`; poll\n`GET /voice/dialer/numbers` and read `caller_id_verified`. An unverified\nTelnyx number is a real number that simply cannot be dialled FROM, which is\nwhy it is kept out of the rotation pool rather than failing mid-session.\n\nSame ownership check as the delete above, for the same reason: voice looks\nthe number up by bare value.","operationId":"verify_voice_caller_id_voice_numbers_verify_caller_id__phone_number__post","parameters":[{"name":"phone_number","in":"path","required":true,"schema":{"type":"string","description":"The number to verify, E.164.","title":"Phone Number"},"description":"The number to verify, E.164."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PhoneNumberPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/numbers/inbound-type":{"patch":{"tags":["Phone Numbers"],"summary":"Change what answers a number's inbound calls","description":"Retype a number between AI answering, SDR answering and the dialer.\n\nNOT a label change, and not free. Moving to `dialer` DESTROYS the LiveKit\ndispatch rule and both SIP trunks and repoints the carrier webhook; moving\naway from it builds them again. The number answers nothing in between, and\nthe teardown is best-effort - a failed trunk delete is logged and the\nretype continues.\n\nRetyping to the mode it is already in is a no-op, so this is safe to retry.\n\nVoice compares the number's own `org_id` against the one sent, and this\nroute sends the API key's - so another organisation's number is a 404\nrather than a silent retype.","operationId":"update_voice_inbound_type_voice_numbers_inbound_type_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VoiceInboundTypeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PhoneNumberPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/numbers/assignee":{"patch":{"tags":["Phone Numbers"],"summary":"Set a number's voice-side assignee","description":"Point a number's voice-side assignment at someone else.\n\nThe VOICE half of `PATCH /phone-numbers/update-assignee`, which does this\nand updates the CDP record. Published separately because the app's\npropagation to voice is best-effort and only logs a warning when it fails -\nso the two records can disagree, and this is the way to reconcile them\nwithout re-running the whole reassignment.\n\nSending `assigned_to: \"\"` clears the assignment. Assigning a WORK number\nalso creates the person's phone-directory row, which is what makes them\nfindable by name to the receptionist.","operationId":"update_voice_assignee_voice_numbers_assignee_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VoiceAssigneeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PhoneNumberPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/numbers/daily-counts":{"delete":{"tags":["Phone Numbers"],"summary":"Reset today's per-number dialing counters","description":"Clear today's outbound call counters for every number in this\norganisation.\n\nTHIS REMOVES A CAP, it does not report on one. Each caller ID has a daily\noutbound limit (40 for US numbers, 60 international) that exists to keep\ncarriers from flagging the number; resetting the counter lets those numbers\ndial past the limit they have already reached today.\n\nADMIN-ONLY, and deliberately stricter than voice, which leaves this route\nungated as an internal operations endpoint with no end-user caller. A\ncustomer-facing key that can quietly lift a carrier-reputation control is\nnot something to publish on the same grant as renaming a number. Machine\nkeys are refused outright.\n\nCounters reset on their own at midnight US Eastern. `deleted` is how many\ncounter keys were actually cleared - zero is a normal answer for an\norganisation that has not dialled today.","operationId":"reset_voice_daily_counts_voice_numbers_daily_counts_delete","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PhoneNumberPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/numbers/answering-agent":{"get":{"tags":["Phone Numbers"],"summary":"Which agent answers a number","description":"Who picks up when this number is called.\n\nA number lives on the company profile as free text while the agent that\nanswers it is bound on that agent's identity, so the link is not readable\nfrom either side alone. This resolves it.\n\nREAD-ONLY by design, and the design is load-bearing: resolving a route for\nreal marks directory members as engaged, so this deliberately does not.","operationId":"get_voice_answering_agent_voice_numbers_answering_agent_get","parameters":[{"name":"number","in":"query","required":false,"schema":{"type":"string","description":"The number to resolve, E.164. OPTIONAL: with no main line set yet, omitting it returns the organisation's receptionists, which is exactly the list to choose one from.","default":"","title":"Number"},"description":"The number to resolve, E.164. OPTIONAL: with no main line set yet, omitting it returns the organisation's receptionists, which is exactly the list to choose one from."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PhoneNumberPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/agents/defaults":{"get":{"tags":["Voice"],"summary":"The organisation's default agent profile","description":"The company facts a newly created agent starts from.\n\nCompany name, services, pain points, value proposition, pitch, FAQs and\nthe default bot persona. This is the seed; `/voice/company-knowledge` is\nthe richer org-wide record that supersedes it for agents that opt in with\n`use_company_knowledge`.","operationId":"get_agent_defaults_voice_agents_defaults_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/agents/global-settings":{"get":{"tags":["Voice"],"summary":"Org-wide inbound call defaults","description":"Which agent answers, in which timezone, and the fallback voicemail.\n\nThese are the ORG's inbound defaults, not any one agent's settings - they\ndecide what happens to a call that no per-number routing rule claims.","operationId":"get_agent_global_settings_voice_agents_global_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"post":{"tags":["Voice"],"summary":"Set org-wide inbound call defaults","description":"Replace the org's inbound defaults.\n\nA REPLACE, not a merge: voice writes the whole settings row, so a field\nleft out is a field cleared. Read the current values first.\n\nPOST rather than PUT because that is the verb voice exposes, and a second\nspelling for the same operation is worse than an imperfect one.\n\n`org_id` is stripped from the body and set from the key.","operationId":"set_agent_global_settings_voice_agents_global_settings_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"`inbound_default_agent_name`, `inbound_default_timezone` and `inbound_default_event_id` are the settings; `contacts` is a JSON STRING, not a list - voice stores it as text.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/agents/receptionist":{"post":{"tags":["Voice"],"summary":"Get the org's receptionist, creating it if absent","description":"IDEMPOTENT: returns the existing receptionist, or creates a default one.\n\nCalling it twice does not produce two receptionists - there is one per\norganisation. That is why it is a POST that is safe to retry, and why it\nis not spelled as a create.","operationId":"ensure_receptionist_agent_voice_agents_receptionist_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"patch":{"tags":["Voice"],"summary":"Turn the receptionist on or off","description":"Enable or disable the receptionist without deleting it.\n\nDisabling stops it answering; its configuration, knowledge and history\nsurvive. This is the switch to use for \"stop answering right now\" -\ndeleting the agent is not reversible.","operationId":"toggle_receptionist_agent_voice_agents_receptionist_patch","parameters":[{"name":"enabled","in":"query","required":true,"schema":{"type":"boolean","description":"Explicit, not a toggle: a retried request is idempotent instead of flipping the receptionist back on.","title":"Enabled"},"description":"Explicit, not a toggle: a retried request is idempotent instead of flipping the receptionist back on."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/agents/clone":{"post":{"tags":["Voice"],"summary":"Clone an agent, or instantiate one from a template","description":"Copy an agent's whole configuration under a new name.\n\nPersona, identity and knowledge attachments come across. This is one call\nwhere `POST /voice/agents` plus a dozen field copies would be several, and\nit is how a template becomes a working agent.\n\nNOT a link: the copy is independent, so later edits to the source do not\nreach it.\n\n`source_agent_id` is resolved WITHIN the caller's org, so a template id\nfrom another tenant simply is not found.","operationId":"clone_agent_voice_agents_clone_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Body_clone_agent_voice_agents_clone_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/agents/{agent_id}/save-as-template":{"post":{"tags":["Voice"],"summary":"Save an agent as a reusable template","description":"Turn a working agent into a starting point for new ones.\n\nThe template is a SNAPSHOT: later changes to the agent do not flow into\nit, and instantiating the template with `POST /voice/agents/clone` does\nnot link back.","operationId":"save_agent_as_template_voice_agents__agent_id__save_as_template_post","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"The agent to templatise.","title":"Agent Id"},"description":"The agent to templatise."},{"name":"template_name","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Template name. Defaults to the agent's own name.","title":"Template Name"},"description":"Template name. Defaults to the agent's own name."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/agents/{agent_id}/memory":{"post":{"tags":["Voice"],"summary":"Record a conversation into an agent's memory of a contact","description":"Teach an agent what was said, so the next call is not the first one.\n\nThis is how a conversation that happened somewhere ELSE - your own product,\na human rep, another channel - becomes context the agent has. Calls the\nagent places itself are recorded already; this route exists for everything\nit did not witness.\n\nWritten to two places by voice: a durable interaction row and the vector\nmemory retrieval reads. There is no delete for a memory on this surface.\n\nThe agent is named in the PATH for a readable URL. Voice's own handler\nscopes the write by `(org_id, contact_id)`, so the memory attaches to the\ncontact within the caller's org either way.","operationId":"update_agent_memory_voice_agents__agent_id__memory_post","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"The agent doing the remembering.","title":"Agent Id"},"description":"The agent doing the remembering."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Body_update_agent_memory_voice_agents__agent_id__memory_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/agents/{agent_id}/skills":{"post":{"tags":["Voice"],"summary":"Give an agent skills it can use","description":"Attach one or more skills. ADDITIVE, not a replace.\n\nThis WIDENS WHAT THE AGENT CAN DO mid-conversation: a skill attached here\nis one the agent may decide to run on a live call, including one that\ncalls an external API. Attach deliberately, and read\n`GET /skills/{action_id}` first if you did not author it.\n\nSkills are resolved within the caller's org, so an id from another tenant\nis not found.","operationId":"attach_skills_to_agent_voice_agents__agent_id__skills_post","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"The agent to equip.","title":"Agent Id"},"description":"The agent to equip."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Body_attach_skills_to_agent_voice_agents__agent_id__skills_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"get":{"tags":["Voice"],"summary":"An agent's skills","description":"SPENDS NOTHING. Every skill attached to the agent, with its full\nconfiguration - the list `POST /voice/agents/{agent_id}/skills` adds to.","operationId":"list_agent_skills_voice_agents__agent_id__skills_get","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Voice agent id.","title":"Agent Id"},"description":"Voice agent id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/agents/{agent_id}/skills/{action_id}":{"delete":{"tags":["Voice"],"summary":"Take a skill away from an agent","description":"Breaks the LINK only - the skill itself survives and other agents keep it.\n\nThe narrow way to stop an agent doing one thing without editing the skill\neveryone else is using.","operationId":"detach_skill_from_agent_voice_agents__agent_id__skills__action_id__delete","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"The agent.","title":"Agent Id"},"description":"The agent."},{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"The skill to remove.","title":"Action Id"},"description":"The skill to remove."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/twins/extract-linkedin":{"post":{"tags":["Voice"],"summary":"Extract a LinkedIn profile to seed a twin","description":"SPENDS CREDITS. Enriches a LinkedIn profile URL into the headline,\ncurrent position, employment history and education a twin is seeded\nfrom. Reaches a paid enrichment provider on your behalf, so it is tiered\n`billable`.\n\nVoice binds `linkedin_url` as a FORM field; the JSON body here is\nre-encoded as form data. Voice answers `{\"success\": false, \"error\": ...}`\nwith a 200 when the profile cannot be extracted - read `success`.\n\nA two-segment LITERAL under `/voice/twins`, declared before the\n`/twins/{agent_id}` routes; `test_voice_stage2_api.py` proves it resolves\nand that `/twins/<id>` still reaches its shipped handler.","operationId":"extract_twin_linkedin_profile_voice_twins_extract_linkedin_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TwinLinkedInExtract"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/twins/{agent_id}":{"get":{"tags":["Voice"],"summary":"Get a digital twin","description":"A twin is an agent modelled on a specific person.\n\nIt shares the agent id space with `/voice/agents` - a twin IS an agent with\n`entity_type: \"twin\"` - so the same id works on both. This route returns\nthe twin-shaped view, including the persona sliders and writing-style\nreferences the agent view does not carry.","operationId":"get_twin_voice_twins__agent_id__get","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Twin id.","title":"Agent Id"},"description":"Twin id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Voice"],"summary":"Delete a digital twin","description":"Delete the twin. NOT REVERSIBLE.\n\nPublished beside `DELETE /voice/agents/{agent_id}` rather than instead of\nit: both remove the same underlying row, and this one is here so a caller\nworking against `/voice/twins` does not have to know that.","operationId":"delete_twin_voice_twins__agent_id__delete","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Twin id.","title":"Agent Id"},"description":"Twin id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"},"put":{"tags":["Voice"],"summary":"Edit a twin, optionally with a new writing-style document","description":"SPENDS NOTHING beyond storage. Partial update: only the fields sent\nchange. Multipart because voice binds every field as a form field so the\noptional writing-style document can travel with them. 404 when the twin\nis not this organisation's.","operationId":"update_twin_voice_twins__agent_id__put","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","description":"Twin agent id.","title":"Agent Id"},"description":"Twin agent id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_update_twin_voice_twins__agent_id__put"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/mcp-servers":{"post":{"tags":["Voice"],"summary":"Connect an MCP server","description":"Register a Model Context Protocol server agents can call tools on.\n\n`transport_type` decides which other field is required: `sse` needs\n`connection_url`, `stdio` needs `command`. It is closed to those two here.\n\n`env_vars` IS A SECRET FIELD. It is write-only by convention on this\nsurface - the read routes return the server's tools, not its environment -\nand anything put here is available to the process voice starts.\n\n`org_id` is not in the body. Voice's own model requires it; it is supplied\nfrom the key, so a caller cannot register a server into another tenant.","operationId":"create_mcp_server_voice_mcp_servers_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/McpServerCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/mcp-servers/{mcp_server_id}":{"put":{"tags":["Voice"],"summary":"Update an MCP server","description":"Partial update. Omitted fields are untouched.\n\n`enabled: false` is the safe way to stop agents using a server: the\nconfiguration survives and the tools stop being offered.","operationId":"update_mcp_server_voice_mcp_servers__mcp_server_id__put","parameters":[{"name":"mcp_server_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"MCP server id.","title":"Mcp Server Id"},"description":"MCP server id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/McpServerUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Voice"],"summary":"Disconnect an MCP server","description":"Remove the server and its stored credentials. NOT REVERSIBLE.\n\nAny agent configured to use its tools loses them. To stop the tools\ntemporarily, update the server with `enabled: false` instead.","operationId":"delete_mcp_server_voice_mcp_servers__mcp_server_id__delete","parameters":[{"name":"mcp_server_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"MCP server id.","title":"Mcp Server Id"},"description":"MCP server id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/mcp-servers/{mcp_server_id}/tools/cached":{"get":{"tags":["Voice"],"summary":"Last known tool list for an MCP server","description":"Read the stored tool list WITHOUT contacting the server.\n\nThis is the one to call in a loop: the live route beside it opens a\nconnection to a third party every time. The two paths differ in LENGTH\nrather than in shape, so neither can shadow the other whichever order they\ntake - `/tools/cached` has a segment `/tools` cannot match.","operationId":"get_cached_mcp_tools_voice_mcp_servers__mcp_server_id__tools_cached_get","parameters":[{"name":"mcp_server_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"MCP server id.","title":"Mcp Server Id"},"description":"MCP server id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/mcp-servers/{mcp_server_id}/tools":{"get":{"tags":["Voice"],"summary":"Live tool list from an MCP server","description":"Ask the MCP server itself what tools it offers.\n\nTHIS REACHES OUTSIDE GRAPH8. The server is one the customer configured, and\nthe connection is made by our infrastructure on their behalf - the same\nreasoning that put `POST /skills/{action_id}/execute` in the `external`\ntier. It is an explicit rule in `build_scope_policy.py::classify`, because\na GET otherwise derives `read` unconditionally and this one is not free of\nside effects: it can hang on an unreachable server, and `refresh=true`\noverwrites the cache the route beside it serves.\n\nUse `/tools/cached` for anything routine.","operationId":"list_mcp_server_tools_voice_mcp_servers__mcp_server_id__tools_get","parameters":[{"name":"mcp_server_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"MCP server id.","title":"Mcp Server Id"},"description":"MCP server id."},{"name":"refresh","in":"query","required":false,"schema":{"type":"boolean","description":"True re-reads from the server and replaces the cache.","default":false,"title":"Refresh"},"description":"True re-reads from the server and replaces the cache."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/skills/infer-variable":{"post":{"tags":["Workflows"],"summary":"Infer one skill variable from a record","description":"Work out what one skill variable should be for a given record.\n\nThe single-variable version of what a skill does to its whole input before\nit runs - useful for showing a caller what a skill WILL see without running\nit. Results are cached per `(org, entity_id)`, so passing `entity_id` makes\na repeated call cheap.","operationId":"infer_skill_variable_skills_infer_variable_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Body_infer_skill_variable_skills_infer_variable_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/skills/parse-script-parameters":{"post":{"tags":["Workflows"],"summary":"Detect a script's parameters from its code","description":"Static analysis, not execution. The code is PARSED and never run.\n\nReturns the detected parameter names with their types and defaults, which\nis how a builder offers the right inputs for a script it did not write.","operationId":"parse_script_parameters_skills_parse_script_parameters_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Body_parse_script_parameters_skills_parse_script_parameters_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/skills/resolve-templates":{"post":{"tags":["Workflows"],"summary":"Resolve skill template names to ids","description":"Turn human template names into the `action_id`s every other route wants.\n\nThe lookup that lets a caller write \"Cold Call Opener\" where the API needs\na UUID. `org_id` is pinned from the key, so a name resolves within the\ncaller's own templates.","operationId":"resolve_skill_templates_skills_resolve_templates_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Template names to resolve, in voice's resolver shape.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/skills/{action_id}/collections":{"get":{"tags":["Workflows"],"summary":"Collections a skill retrieves from","description":"What this skill can look things up in while it runs.\n\nThe collections themselves are managed at `/voice/collections`; this is\nthe link between one skill and them.","operationId":"list_skill_collections_skills__action_id__collections_get","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill or workflow `action_id`.","title":"Action Id"},"description":"Skill or workflow `action_id`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"},"post":{"tags":["Workflows"],"summary":"Give a skill collections to retrieve from","description":"ADDITIVE, not a replace: attaching does not detach what is already there.\n\nTakes effect on the next run. A collection with no vectors retrieves\nnothing - check `/voice/collections/{id}/vector-status` if a skill seems\nto be ignoring what you gave it.","operationId":"attach_skill_collections_skills__action_id__collections_post","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill or workflow `action_id`.","title":"Action Id"},"description":"Skill or workflow `action_id`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Body_attach_skill_collections_skills__action_id__collections_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/skills/{action_id}/collections/{collection_id}":{"delete":{"tags":["Workflows"],"summary":"Stop a skill retrieving from a collection","description":"Breaks the LINK only. The collection and its files are untouched.","operationId":"detach_skill_collection_skills__action_id__collections__collection_id__delete","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill or workflow `action_id`.","title":"Action Id"},"description":"Skill or workflow `action_id`."},{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection to unlink.","title":"Collection Id"},"description":"Collection to unlink."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"workflows:delete","x-graph8-lifecycle":"active"}},"/skills/{action_id}/versions/{version_id}/diff":{"get":{"tags":["Workflows"],"summary":"Diff two versions of a skill","description":"Field-level diff - what actually changed, not just that something did.\n\nThe question to ask when a skill's output changed and nobody remembers\nediting it.","operationId":"diff_skill_versions_skills__action_id__versions__version_id__diff_get","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill or workflow `action_id`.","title":"Action Id"},"description":"Skill or workflow `action_id`."},{"name":"version_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"The version to diff.","title":"Version Id"},"description":"The version to diff."},{"name":"against","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"The version to compare with. Defaults to the one immediately before.","title":"Against"},"description":"The version to compare with. Defaults to the one immediately before."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/skills/{action_id}/test-cases":{"get":{"tags":["Workflows"],"summary":"List a skill's saved test cases","description":"Oldest first, so the suite has a stable order between runs.","operationId":"list_skill_test_cases_skills__action_id__test_cases_get","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill or workflow `action_id`.","title":"Action Id"},"description":"Skill or workflow `action_id`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"},"post":{"tags":["Workflows"],"summary":"Save a test case for a skill","description":"Saving a case RUNS NOTHING. Only `POST .../test-runs` runs the skill.\n\nThat separation is the point: building a suite is free, and executing it\nis the operation that costs.","operationId":"create_skill_test_case_skills__action_id__test_cases_post","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill or workflow `action_id`.","title":"Action Id"},"description":"Skill or workflow `action_id`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Body_create_skill_test_case_skills__action_id__test_cases_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/skills/{action_id}/test-cases/{test_case_id}":{"put":{"tags":["Workflows"],"summary":"Update a test case","description":"PARTIAL update despite the verb - voice exposes it as a PUT.\n\nOmitted fields are untouched; an explicit `null` CLEARS the field. Those\nare different instructions and only the second one is destructive.","operationId":"update_skill_test_case_skills__action_id__test_cases__test_case_id__put","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill or workflow `action_id`.","title":"Action Id"},"description":"Skill or workflow `action_id`."},{"name":"test_case_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Test case id.","title":"Test Case Id"},"description":"Test case id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Any of `name`, `input_data`, `expected_output`, `assertion_type`, `assertion_config`.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Workflows"],"summary":"Delete a test case","description":"The case goes; its HISTORICAL RUNS SURVIVE, still carrying its id.\n\nSo a deleted case leaves readable history rather than orphaning it - past\nruns in `GET .../test-runs` keep working.","operationId":"delete_skill_test_case_skills__action_id__test_cases__test_case_id__delete","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill or workflow `action_id`.","title":"Action Id"},"description":"Skill or workflow `action_id`."},{"name":"test_case_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Test case id.","title":"Test Case Id"},"description":"Test case id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"workflows:delete","x-graph8-lifecycle":"active"}},"/skills/{action_id}/test-runs":{"get":{"tags":["Workflows"],"summary":"A skill's test-run history","description":"Newest first. Reading history costs nothing and runs nothing.","operationId":"list_skill_test_runs_skills__action_id__test_runs_get","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill or workflow `action_id`.","title":"Action Id"},"description":"Skill or workflow `action_id`."},{"name":"test_case_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only runs of this case.","title":"Test Case Id"},"description":"Only runs of this case."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Rows to return, newest first.","default":50,"title":"Limit"},"description":"Rows to return, newest first."},{"name":"include_output","in":"query","required":false,"schema":{"type":"boolean","description":"True adds the stored output previews. They can be large.","default":false,"title":"Include Output"},"description":"True adds the stored output previews. They can be large."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"},"post":{"tags":["Workflows"],"summary":"Run every saved test case against a skill","description":"RUNS THE SKILL, ONCE PER SAVED CASE. This has real side effects.\n\nFor an `llm` skill that is a model call per case. For an `api` skill it is\nan outbound HTTP request per case, to the endpoint the skill is configured\nwith, made AS THE PLATFORM - so a skill that writes somewhere will write\nthere again, with the fixture's data.\n\nEvery case is pinned to ONE version of the skill, so the result is a\nregression answer rather than a mix of versions.\n\nTiered `external` by an explicit rule, for the same reason\n`POST /skills/{action_id}/execute` is: it reaches outside graph8 on the\ncustomer's behalf, and nothing in the path name says so.","operationId":"run_skill_test_suite_skills__action_id__test_runs_post","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill or workflow `action_id`.","title":"Action Id"},"description":"Skill or workflow `action_id`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/workflows/executions/bulk-restart":{"post":{"tags":["Workflows"],"summary":"Restart many workflow executions","description":"\"Re-run all failed\", in one call. EVERY NODE RUNS AGAIN.\n\nNot a resume: a restart begins at the start, so nodes that already\nsucceeded run a second time - including anything that sent a message,\ncalled an API or spent credits the first time.\n\nVoice applies a 60-second idempotency window to this route, so an\naccidental double-submit inside that window does not double-run the batch.\nSend an `Idempotency-Key` header as well for the app-wide guard.\n\nEvery execution in the batch is scoped to the caller's org before it is\ntouched; ids belonging to another tenant are simply not found.\n\nA restart runs each workflow as it is NOW. When one has record steps or a\nrecord trigger, the key needs the object scopes they exercise (403\n``missing_scopes`` refuses the whole batch, nothing restarts), and only the\nworkflow's owner or a graph8 admin may restart it: for any other member that\nitem is reported in ``failed`` with ``owner_or_admin_required`` while the\nrest of the batch goes ahead. When graph8 cannot confirm who is an admin,\nthat item is refused, never guessed, and also reported in ``failed``.","operationId":"bulk_restart_executions_workflows_executions_bulk_restart_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Which executions to restart, in voice's batch shape (e.g. `execution_ids`).","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/workflows/executions/request-changes":{"post":{"tags":["Workflows"],"summary":"Answer a human-approval step with changes requested","description":"The THIRD outcome of a human-approval step, beside approve and reject.\n\nApprove and reject are terminal for the paused node. This one is not: it\nsends the run down the revise branch carrying the reviewer's words, so the\nworkflow gets another attempt instead of ending.","operationId":"request_execution_changes_workflows_executions_request_changes_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Body_request_execution_changes_workflows_executions_request_changes_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/workflows/executions/{execution_id}/restart":{"post":{"tags":["Workflows"],"summary":"Restart one workflow execution","description":"Runs the workflow again FROM THE BEGINNING. Not a resume.\n\nNodes that already succeeded run a second time. If any of them sent an\nemail, posted to Slack or called a paid API, they do it again. To continue\na paused run instead, use `POST /workflows/executions/{id}/resume`.\n\nThe org is forwarded and voice scopes the lookup by it, so one tenant\ncannot restart another's run.\n\nA restart runs the workflow as it is NOW, with the original or new input.\nWhen it has record steps or a record trigger, the key needs the object\nscopes they exercise (403 ``missing_scopes``), and only the workflow's\nowner or a graph8 admin may restart it, with reused or new input (403\n``owner_or_admin_required``). When graph8 cannot confirm who is an admin the\nrestart is refused, never guessed: the workflow service answers 503, which\nreaches the caller as ``502`` like its other upstream failures; retry later.","operationId":"restart_execution_workflows_executions__execution_id__restart_post","parameters":[{"name":"execution_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Execution id.","title":"Execution Id"},"description":"Execution id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Optional restart overrides.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/workflows/run-summary":{"get":{"tags":["Workflows"],"summary":"Has this workflow ever run?","description":"The authoritative answer for a BATCH of workflows, in one call.\n\nWorth using instead of listing executions per workflow: \"never run\" and\n\"ran and returned nothing\" look identical in an empty execution list, and\nthis distinguishes them.","operationId":"get_workflow_run_summary_workflows_run_summary_get","parameters":[{"name":"action_ids","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated workflow ids. Omit for every workflow in the org.","title":"Action Ids"},"description":"Comma-separated workflow ids. Omit for every workflow in the org."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/node-stats":{"get":{"tags":["Workflows"],"summary":"Per-node success and failure rates for a workflow","description":"Which STEP is failing, aggregated across runs.\n\nThe view that turns \"this workflow is flaky\" into \"this node times out\",\nwithout reading every execution.","operationId":"get_workflow_node_stats_workflows_node_stats_get","parameters":[{"name":"action_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"description":"The workflow to analyse.","title":"Action Id"},"description":"The workflow to analyse."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Window, in days.","default":30,"title":"Days"},"description":"Window, in days."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/{action_id}/runs/recent":{"get":{"tags":["Workflows"],"summary":"Recent runs of one workflow","description":"Ordered and limited in SQL, so a busy workflow answers cheaply.\n\n`GET /workflows/executions` lists across the whole org; this is the\nper-workflow view.","operationId":"list_recent_workflow_runs_workflows__action_id__runs_recent_get","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill or workflow `action_id`.","title":"Action Id"},"description":"Skill or workflow `action_id`."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Rows to return, newest first.","default":10,"title":"Limit"},"description":"Rows to return, newest first."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/integrations":{"get":{"tags":["Workflows"],"summary":"List connected workflow integrations","description":"Which third-party accounts workflow nodes can act as.\n\nRows report `has_api_key` rather than the key: credentials on this surface\nare write-only and are never echoed back.","operationId":"list_workflow_integrations_workflows_integrations_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/integrations/{provider_name}":{"get":{"tags":["Workflows"],"summary":"Get one workflow integration","description":"Its configuration and whether a key is stored - never the key itself.","operationId":"get_workflow_integration_workflows_integrations__provider_name__get","parameters":[{"name":"provider_name","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Provider name.","title":"Provider Name"},"description":"Provider name."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"},"post":{"tags":["Workflows"],"summary":"Connect or update a workflow integration","description":"UPSERT: creates the integration or replaces its configuration.\n\nPOST rather than PUT because that is the verb voice exposes, and one\nspelling is better than two.\n\nWhatever is stored here is used BY WORKFLOW NODES ACTING AS THE PLATFORM,\nso a key placed here is a standing grant, not a one-off.","operationId":"save_workflow_integration_workflows_integrations__provider_name__post","parameters":[{"name":"provider_name","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Provider name.","title":"Provider Name"},"description":"Provider name."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Body_save_workflow_integration_workflows_integrations__provider_name__post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Workflows"],"summary":"Disconnect a workflow integration","description":"Removes the stored credential and configuration. NOT REVERSIBLE.\n\nAny workflow node using this provider starts failing at its next run.","operationId":"delete_workflow_integration_workflows_integrations__provider_name__delete","parameters":[{"name":"provider_name","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Provider name.","title":"Provider Name"},"description":"Provider name."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"workflows:delete","x-graph8-lifecycle":"active"}},"/voice/collections":{"post":{"tags":["Voice"],"summary":"Create a knowledge collection","description":"Create an empty collection for an agent to retrieve from.\n\nVoice takes `name` and `description` as QUERY parameters. They are a JSON\nbody here because a description is prose - putting it in a URL means\nlength limits and encoding bugs for the one field most likely to contain a\nnewline. The bounds are voice's own.","operationId":"create_collection_voice_collections_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CollectionCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"get":{"tags":["Voice"],"summary":"List knowledge collections","description":"Every collection in the organisation.","operationId":"list_collections_voice_collections_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/collections/files":{"get":{"tags":["Voice"],"summary":"List every file across every collection","description":"One flat view of the whole knowledge base.\n\nDeclared BEFORE `/collections/{collection_id}`: that route parses an\ninteger, so a flipped order would answer 422 for this path rather than\n404 - a failure that reads like a bad request instead of a missing route.","operationId":"list_all_collection_files_voice_collections_files_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}":{"get":{"tags":["Voice"],"summary":"Get one collection","description":"One collection, with its file count and indexing state.","operationId":"get_collection_voice_collections__collection_id__get","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"put":{"tags":["Voice"],"summary":"Rename or re-describe a collection","description":"Change a collection's name or description. Files are untouched.","operationId":"update_collection_voice_collections__collection_id__put","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CollectionUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Voice"],"summary":"Delete a collection and everything in it","description":"Delete the collection, its files and its vectors. NOT REVERSIBLE.\n\nAny agent retrieving from it stops retrieving from it; the agent itself\nsurvives and simply loses that source.","operationId":"delete_collection_voice_collections__collection_id__delete","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}/files/download-url":{"get":{"tags":["Voice"],"summary":"Get a temporary download URL for one file","description":"Return a PRE-SIGNED URL for the file. This does not return the file.\n\nNamed `download-url` rather than `download` for exactly that reason: the\nknowledge-base route that really does stream bytes is deliberately not\npublished, and two routes called `download` that behave differently would\nbe worse than either.","operationId":"get_collection_file_download_url_voice_collections__collection_id__files_download_url_get","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"filename","in":"query","required":true,"schema":{"type":"string","description":"File name within the collection.","title":"Filename"},"description":"File name within the collection."},{"name":"folder_path","in":"query","required":false,"schema":{"type":"string","description":"Folder inside the collection. Empty is the root.","default":"","title":"Folder Path"},"description":"Folder inside the collection. Empty is the root."},{"name":"expiration","in":"query","required":false,"schema":{"type":"integer","maximum":86400,"minimum":60,"description":"How long the URL stays valid, in seconds.","default":3600,"title":"Expiration"},"description":"How long the URL stays valid, in seconds."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}/files/exists":{"get":{"tags":["Voice"],"summary":"Check whether a file is already in a collection","description":"Answers the question an upload flow asks before it overwrites.","operationId":"check_collection_file_exists_voice_collections__collection_id__files_exists_get","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"filename","in":"query","required":true,"schema":{"type":"string","description":"File name to look for.","title":"Filename"},"description":"File name to look for."},{"name":"folder_path","in":"query","required":false,"schema":{"type":"string","description":"Folder inside the collection.","default":"","title":"Folder Path"},"description":"Folder inside the collection."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}/files/rename":{"put":{"tags":["Voice"],"summary":"Rename or move a file within a collection","description":"Rename a file, move it between folders, or both in one call.\n\nThe vector rows follow the file - this is a rename, not a re-index, so\nretrieval keeps working and nothing is re-embedded.","operationId":"rename_collection_file_voice_collections__collection_id__files_rename_put","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"old_filename","in":"query","required":true,"schema":{"type":"string","description":"Current file name.","title":"Old Filename"},"description":"Current file name."},{"name":"new_filename","in":"query","required":true,"schema":{"type":"string","description":"New file name.","title":"New Filename"},"description":"New file name."},{"name":"old_folder_path","in":"query","required":false,"schema":{"type":"string","description":"Current folder. Empty is the root.","default":"","title":"Old Folder Path"},"description":"Current folder. Empty is the root."},{"name":"new_folder_path","in":"query","required":false,"schema":{"type":"string","description":"Target folder. Empty is the root.","default":"","title":"New Folder Path"},"description":"Target folder. Empty is the root."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}/files/all":{"delete":{"tags":["Voice"],"summary":"Delete every file in a collection","description":"Empty the collection. The collection itself survives, with no content.\n\nNOT REVERSIBLE, and there is no confirmation step - the separate path\nsegment is the confirmation, which is why this is not `DELETE .../files`\nwith the filename left off.","operationId":"delete_all_collection_files_voice_collections__collection_id__files_all_delete","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}/files":{"delete":{"tags":["Voice"],"summary":"Delete one file from a collection","description":"Remove one file and its vectors.\n\n`filename` is REQUIRED so this can never be mistaken for the bulk delete\nbeside it. Emptying a collection is `DELETE .../files/all`, on purpose.","operationId":"delete_collection_file_voice_collections__collection_id__files_delete","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"filename","in":"query","required":true,"schema":{"type":"string","minLength":1,"description":"The file to remove. REQUIRED - there is no 'delete everything' by omission.","title":"Filename"},"description":"The file to remove. REQUIRED - there is no 'delete everything' by omission."},{"name":"folder_path","in":"query","required":false,"schema":{"type":"string","description":"Folder inside the collection.","default":"","title":"Folder Path"},"description":"Folder inside the collection."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}/vector-status":{"get":{"tags":["Voice"],"summary":"Indexing status for a collection","description":"Whether the collection is actually retrievable yet, and how much of it.\n\nA file being present is not the same as a file being indexed. Read this\nbefore concluding an agent is ignoring its knowledge.","operationId":"get_collection_vector_status_voice_collections__collection_id__vector_status_get","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}/reindex":{"post":{"tags":["Voice"],"summary":"Rebuild a collection's vector index","description":"RE-EMBEDS EVERY FILE IN THE COLLECTION. This costs money.\n\nEmbedding is charged per token, so the cost is proportional to the whole\ncollection, not to whatever changed. Use it to recover from a bad index,\nnot as a routine refresh - adding a file already indexes that file.\n\nTiered `billable` by an explicit rule rather than by name: nothing in the\nword \"reindex\" matches a billable path marker, and as a plain `write` this\nwould ride along with \"rename a collection\".","operationId":"reindex_collection_voice_collections__collection_id__reindex_post","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}/vectors":{"delete":{"tags":["Voice"],"summary":"Clear a collection's vectors, keeping the files","description":"Drop the index and keep the source files.\n\nRetrieval stops returning anything from this collection until it is\nreindexed - which re-embeds everything and is charged. The files are NOT\ndeleted, which is the whole difference from `DELETE .../files/all`.","operationId":"clear_collection_vectors_voice_collections__collection_id__vectors_delete","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}/scrape-sources":{"get":{"tags":["Voice"],"summary":"List the web sources feeding a collection","description":"Each row carries its last run, page count and last error.","operationId":"list_scrape_sources_voice_collections__collection_id__scrape_sources_get","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"post":{"tags":["Voice"],"summary":"Attach a web source and crawl it now","description":"Crawl a site into this collection, now and then on a schedule.\n\nTHE FIRST CRAWL STARTS IMMEDIATELY. It does not wait for the cadence, so\ncreating a source with `frequency: manual` still crawls once. Up to\n`max_pages` pages are fetched and embedded, and both cost money - which is\nwhy this is `billable` and voice guards it with its EXPENSIVE rate limit.\n\n`frequency` is closed to voice's four cadences here. Voice itself takes a\nbare string and only its scheduler notices an unknown one, so an invented\nvalue there produces a source that quietly never re-crawls.","operationId":"create_scrape_source_voice_collections__collection_id__scrape_sources_post","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ScrapeSourceCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}/scrape-sources/{source_id}":{"patch":{"tags":["Voice"],"summary":"Change a web source's cadence, ceiling, or pause it","description":"Reconciles the schedule as well as the row.\n\n`enabled: false` PAUSES the recurring crawl and keeps everything already\ncrawled. Unlike creating a source, this does not crawl immediately.","operationId":"update_scrape_source_voice_collections__collection_id__scrape_sources__source_id__patch","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"source_id","in":"path","required":true,"schema":{"type":"integer","description":"Scrape source id.","title":"Source Id"},"description":"Scrape source id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ScrapeSourceUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Voice"],"summary":"Remove a web source and the file it maintained","description":"Deletes the schedule, the managed file and its vectors, then the row.\n\nWider than it sounds: the crawled content goes too. To stop crawling but\nkeep what was crawled, PATCH the source with `enabled: false` instead.","operationId":"delete_scrape_source_voice_collections__collection_id__scrape_sources__source_id__delete","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"source_id","in":"path","required":true,"schema":{"type":"integer","description":"Scrape source id.","title":"Source Id"},"description":"Scrape source id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/company-knowledge":{"get":{"tags":["Voice"],"summary":"Get the organisation's company knowledge","description":"What the company does, said once, for every agent to inherit.\n\nVoice takes the organisation as a PATH segment here. It is not one on this\nsurface: an org id in a public path invites a caller to change it, and the\nonly correct value is the one on the key.","operationId":"get_company_knowledge_voice_company_knowledge_get","parameters":[{"name":"use_cache","in":"query","required":false,"schema":{"type":"boolean","description":"False forces a fresh read. The cache is short-lived; prefer the default.","default":true,"title":"Use Cache"},"description":"False forces a fresh read. The cache is short-lived; prefer the default."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"post":{"tags":["Voice"],"summary":"Create the organisation's company knowledge","description":"Set the org-wide knowledge for the first time.\n\nThere is ONE record per organisation - 409 if it already exists, and the\nupdate route is how you change it.\n\nThe body is forwarded as given rather than re-declared field by field. The\nrecord is twenty-odd fields wide and voice owns it; a mirror here would be\na second place to forget one. `org_id` is the exception: it is stripped\nfrom anything the caller sends and set from the key, so a body cannot name\nanother tenant.","operationId":"create_company_knowledge_voice_company_knowledge_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Company knowledge record. `company_name`, `company_description`, `value_proposition`, `pitch`, `bot_name`, `bot_personality`, `persona` and `target_audience` are required; the list fields (`company_services`, `company_products`, `customer_pain_points`, `faqs`) default to empty.","title":"Payload"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"put":{"tags":["Voice"],"summary":"Update the organisation's company knowledge","description":"Partial update - every field is optional.\n\nTakes effect on the next conversation each agent starts; calls already in\nprogress keep the prompt they began with.","operationId":"update_company_knowledge_voice_company_knowledge_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Fields to change. Omitted fields are left alone.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/company-knowledge/formatted":{"get":{"tags":["Voice"],"summary":"Get company knowledge as the agent prompt sees it","description":"The rendered prompt block, not the structured record.\n\nThis is the preview worth reading before wondering why an agent says\nsomething odd: it shows the exact text the model is given.","operationId":"get_formatted_company_knowledge_voice_company_knowledge_formatted_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/knowledge-base/files":{"delete":{"tags":["Voice"],"summary":"Delete a knowledge-base file","description":"Remove one file from the org-wide knowledge base.\n\nThis is the OLDER, flat knowledge store that predates collections. New\ncontent belongs in a collection; these two routes exist so an org that\nstill has files here can manage them.","operationId":"delete_knowledge_base_file_voice_knowledge_base_files_delete","parameters":[{"name":"filename","in":"query","required":true,"schema":{"type":"string","minLength":1,"description":"The file to remove.","title":"Filename"},"description":"The file to remove."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"},"get":{"tags":["Voice"],"summary":"Files in the organisation knowledge base","description":"SPENDS NOTHING. The names `GET /voice/knowledge-base/files/download`,\n`.../rename` and the delete route take.","operationId":"list_knowledge_base_files_voice_knowledge_base_files_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/knowledge-base/files/rename":{"put":{"tags":["Voice"],"summary":"Rename a knowledge-base file","description":"Rename one file in the org-wide knowledge base.","operationId":"rename_knowledge_base_file_voice_knowledge_base_files_rename_put","parameters":[{"name":"old_filename","in":"query","required":true,"schema":{"type":"string","minLength":1,"description":"Current name.","title":"Old Filename"},"description":"Current name."},{"name":"new_filename","in":"query","required":true,"schema":{"type":"string","minLength":1,"description":"New name.","title":"New Filename"},"description":"New name."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/agent-documents/{document_id}":{"delete":{"tags":["Voice"],"summary":"Delete a document from an agent's own store","description":"Delete a document and every chunk it was split into.\n\nAn agent's own documents are separate from collections: a collection is\nshared and attachable, this store belongs to one agent. The upload side is\n`multipart/form-data` and is not published - see the module docstring.","operationId":"delete_agent_document_voice_agent_documents__document_id__delete","parameters":[{"name":"document_id","in":"path","required":true,"schema":{"type":"integer","description":"Document id.","title":"Document Id"},"description":"Document id."},{"name":"agent_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"description":"The agent the document belongs to. Required: document ids are scoped per agent.","title":"Agent Id"},"description":"The agent the document belongs to. Required: document ids are scoped per agent."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}/files/paste-text":{"post":{"tags":["Voice"],"summary":"Create a text file in a collection from pasted content","description":"SPENDS CREDITS. Stores the pasted text as a `.txt` file in the\ncollection and indexes it for retrieval - the indexing embeds the text\nagainst a paid model, which is why this is `billable` like `reindex`.\n\nVoice binds this body as FORM fields (`org_id`, `folder_path`, `filename`,\n`text_content`); the JSON here is re-encoded, with the organisation taken\nfrom the key. Given a filename with no extension, voice appends `.txt`.","operationId":"paste_text_into_collection_voice_collections__collection_id__files_paste_text_post","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CollectionPasteText"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/calls/{call_id}/artifacts":{"get":{"tags":["Voice"],"summary":"Whether a call's transcript and recording are ready","description":"Readiness, not content. Deliberately returns NO storage URL.\n\nPoll this instead of retrying a transcript fetch: a call that has just\nended has a row long before it has a transcript, and this distinguishes\n\"not yet\" from \"never\".","operationId":"get_call_artifacts_voice_calls__call_id__artifacts_get","parameters":[{"name":"call_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Call id.","title":"Call Id"},"description":"Call id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/inbound-calls/pending":{"get":{"tags":["Voice"],"summary":"Inbound calls ringing right now","description":"Calls waiting to be picked up, with caller info and how long they have waited.\n\nA live view: rows disappear as calls are answered, declined or abandoned.\nAnything durable about a call that already ended is in\n`/voice/call-results/search`.","operationId":"list_pending_inbound_calls_voice_inbound_calls_pending_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/inbound-calls/{room_name}/claim":{"post":{"tags":["Voice"],"summary":"Claim a ringing inbound call for one rep","description":"FIRST WINS. A second claim on the same call loses, and says so.\n\nThis CONNECTS A HUMAN TO A LIVE CALLER. It is the race-resolution step the\nnotification socket exists to drive; calling it from an automation means\ndeciding who answers before a person has seen the call.","operationId":"claim_inbound_call_voice_inbound_calls__room_name__claim_post","parameters":[{"name":"room_name","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"The ringing call's room name.","title":"Room Name"},"description":"The ringing call's room name."},{"name":"sdr_email","in":"query","required":true,"schema":{"type":"string","description":"The rep taking it.","title":"Sdr Email"},"description":"The rep taking it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/inbound-calls/decline":{"post":{"tags":["Voice"],"summary":"Decline or hang up a ringing inbound call","description":"ENDS A CALL A REAL PERSON IS ON. There is no undo.\n\nDeclining sends the caller onward - to voicemail or the next rule - rather\nthan simply dropping them, which is the difference from `action: hangup`.","operationId":"decline_inbound_call_voice_inbound_calls_decline_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Body_decline_inbound_call_voice_inbound_calls_decline_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/inbound-calls/dialer/{call_id}/decline":{"post":{"tags":["Voice"],"summary":"Decline an inbound call arriving during a dialer session","description":"The dialer's own decline, for a call that interrupts a session.\n\nSeparate from `/voice/inbound-calls/decline` because the identifier is\ndifferent - a dialer call id, not a room name - and so is the effect: the\nrep stays in their session rather than returning to the idle queue.","operationId":"decline_dialer_inbound_call_voice_inbound_calls_dialer__call_id__decline_post","parameters":[{"name":"call_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Dialer call id.","title":"Call Id"},"description":"Dialer call id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/voicemails":{"get":{"tags":["Voice"],"summary":"List voicemails","description":"Messages left when nobody answered, newest first.","operationId":"list_voicemails_voice_voicemails_get","parameters":[{"name":"is_read","in":"query","required":false,"schema":{"anyOf":[{"type":"boolean"},{"type":"null"}],"description":"True for read only, false for unread only. Omit for both.","title":"Is Read"},"description":"True for read only, false for unread only. Omit for both."},{"name":"sdr_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only voicemails assigned to this rep.","title":"Sdr Email"},"description":"Only voicemails assigned to this rep."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Rows per page.","default":50,"title":"Limit"},"description":"Rows per page."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Rows to skip.","default":0,"title":"Offset"},"description":"Rows to skip."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/voicemails/read-all":{"patch":{"tags":["Voice"],"summary":"Mark every voicemail read","description":"Bulk-clear unread voicemail. Read the `assigned_to` note first.\n\nDeclared BEFORE `/voicemails/{voicemail_id}/read`: `read-all` is a literal\nthat the parameter route could otherwise capture as a voicemail id, and\nthat route parses an integer, so the failure would be a 422 rather than an\nobvious 404.","operationId":"mark_all_voicemails_read_voice_voicemails_read_all_patch","parameters":[{"name":"sdr_email","in":"query","required":true,"schema":{"type":"string","description":"Who is marking them read. Recorded against each row.","title":"Sdr Email"},"description":"Who is marking them read. Recorded against each row."},{"name":"assigned_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to one rep's voicemails. OMITTING THIS CLEARS THE WHOLE ORGANISATION'S unread state, not just this rep's.","title":"Assigned To"},"description":"Narrow to one rep's voicemails. OMITTING THIS CLEARS THE WHOLE ORGANISATION'S unread state, not just this rep's."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/voicemails/{voicemail_id}/read":{"patch":{"tags":["Voice"],"summary":"Mark one voicemail read","description":"One-way: there is no route to mark a voicemail unread again.","operationId":"mark_voicemail_read_voice_voicemails__voicemail_id__read_patch","parameters":[{"name":"voicemail_id","in":"path","required":true,"schema":{"type":"integer","description":"Voicemail id.","title":"Voicemail Id"},"description":"Voicemail id."},{"name":"sdr_email","in":"query","required":true,"schema":{"type":"string","description":"Who read it. Recorded against the row.","title":"Sdr Email"},"description":"Who read it. Recorded against the row."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/voicemails/{voicemail_id}/archive":{"patch":{"tags":["Voice"],"summary":"Archive a voicemail","description":"Hide a voicemail from the default list. Reversible; the recording is kept.\n\nA voicemail of another organisation is the same 404 as a missing one (voice checks the\norganisation, which comes from the key).","operationId":"archive_voicemail_voice_voicemails__voicemail_id__archive_patch","parameters":[{"name":"voicemail_id","in":"path","required":true,"schema":{"type":"integer","description":"Voicemail id.","title":"Voicemail Id"},"description":"Voicemail id."},{"name":"sdr_email","in":"query","required":true,"schema":{"type":"string","description":"Who is archiving it. Recorded as `archived_by`.","title":"Sdr Email"},"description":"Who is archiving it. Recorded as `archived_by`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/voicemails/{voicemail_id}/unarchive":{"patch":{"tags":["Voice"],"summary":"Unarchive a voicemail","description":"Put an archived voicemail back on the default list.","operationId":"unarchive_voicemail_voice_voicemails__voicemail_id__unarchive_patch","parameters":[{"name":"voicemail_id","in":"path","required":true,"schema":{"type":"integer","description":"Voicemail id.","title":"Voicemail Id"},"description":"Voicemail id."},{"name":"sdr_email","in":"query","required":true,"schema":{"type":"string","description":"Who is restoring it.","title":"Sdr Email"},"description":"Who is restoring it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/voicemails/{voicemail_id}/star":{"patch":{"tags":["Voice"],"summary":"Star a voicemail","description":"Star a voicemail.","operationId":"star_voicemail_voice_voicemails__voicemail_id__star_patch","parameters":[{"name":"voicemail_id","in":"path","required":true,"schema":{"type":"integer","description":"Voicemail id.","title":"Voicemail Id"},"description":"Voicemail id."},{"name":"sdr_email","in":"query","required":true,"schema":{"type":"string","description":"Who is starring it.","title":"Sdr Email"},"description":"Who is starring it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/voicemails/{voicemail_id}/unstar":{"patch":{"tags":["Voice"],"summary":"Remove a voicemail's star","description":"Remove a voicemail's star.","operationId":"unstar_voicemail_voice_voicemails__voicemail_id__unstar_patch","parameters":[{"name":"voicemail_id","in":"path","required":true,"schema":{"type":"integer","description":"Voicemail id.","title":"Voicemail Id"},"description":"Voicemail id."},{"name":"sdr_email","in":"query","required":true,"schema":{"type":"string","description":"Who is removing the star.","title":"Sdr Email"},"description":"Who is removing the star."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/inbound-routing/rules":{"get":{"tags":["Voice"],"summary":"List inbound routing rules","description":"Rules are evaluated in ASCENDING `priority` and the first match wins.\n\nRead them in order to know what a call on a number will actually do - a\nlater rule that looks right may never be reached.","operationId":"list_inbound_routes_voice_inbound_routing_rules_get","parameters":[{"name":"phone_number","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only rules for this number.","title":"Phone Number"},"description":"Only rules for this number."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"post":{"tags":["Voice"],"summary":"Create an inbound routing rule","description":"Decide where calls on one number go.\n\nTHIS CHANGES WHAT HAPPENS TO REAL CALLERS as soon as it is active. A rule\nwith a lower `priority` than an existing one takes precedence over it, so\ncreating a rule can silently retire the one that was working.\n\n`target_type` and `ring_strategy` are closed to voice's own sets. `org_id`\nis absent from the body and pinned from the key.","operationId":"create_inbound_route_voice_inbound_routing_rules_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/InboundRouteCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/inbound-routing/rules/{route_id}":{"patch":{"tags":["Voice"],"summary":"Update an inbound routing rule","description":"Partial update. Omitted fields are untouched.\n\n`is_active: false` is the reversible way to take a rule out of the running.\nDeleting it is not.","operationId":"update_inbound_route_voice_inbound_routing_rules__route_id__patch","parameters":[{"name":"route_id","in":"path","required":true,"schema":{"type":"integer","description":"Rule id.","title":"Route Id"},"description":"Rule id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/InboundRouteUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Voice"],"summary":"Delete an inbound routing rule","description":"Remove a rule. Calls it used to catch fall through to the next match.\n\nIf it was the only rule for that number, callers reach whatever the org\ndefault is - check `/voice/agents/global-settings` before deleting the\nlast one.","operationId":"delete_inbound_route_voice_inbound_routing_rules__route_id__delete","parameters":[{"name":"route_id","in":"path","required":true,"schema":{"type":"integer","description":"Rule id.","title":"Route Id"},"description":"Rule id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/inbound-routing/business-hours":{"get":{"tags":["Voice"],"summary":"Read the business-hours schedule for a number","description":"Reconstructed from the underlying rules, not stored separately.\n\n`enabled: false` means no business-hours PAIR exists - there may still be\nordinary rules on the number. This is a view over `/rules`, not a second\nsource of truth.","operationId":"get_business_hours_voice_inbound_routing_business_hours_get","parameters":[{"name":"phone_number","in":"query","required":true,"schema":{"type":"string","description":"The number to read.","title":"Phone Number"},"description":"The number to read."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"put":{"tags":["Voice"],"summary":"Set the business-hours schedule for a number","description":"Create or REPLACE the open-hours / after-hours rule pair.\n\nA PUT because it is a replace: calling it twice leaves two rules, not\nfour. It writes into the same rule list `/voice/inbound-routing/rules`\nmanages, so a hand-made rule at a lower priority still wins over it.\n\n`timezone` is an IANA name and voice rejects anything it cannot load, so\na schedule cannot silently run in UTC.","operationId":"upsert_business_hours_voice_inbound_routing_business_hours_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BusinessHoursScheduleRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Voice"],"summary":"Remove the business-hours schedule for a number","description":"Deletes BOTH rules in the pair, disabling the schedule.\n\nAfter this, calls on the number are handled by whatever other rules exist,\nat every hour of the day.","operationId":"delete_business_hours_voice_inbound_routing_business_hours_delete","parameters":[{"name":"phone_number","in":"query","required":true,"schema":{"type":"string","description":"The number to clear.","title":"Phone Number"},"description":"The number to clear."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/voice-library/presets":{"get":{"tags":["Voice"],"summary":"List the preset voices an agent can speak with","description":"The public preset catalogue - the source of `voice` ids for an agent.\n\nNot org-specific: these are the shared presets, the same for every\norganisation. Cloned voices belong to an org and are not listed here.\n\nVoice falls back to a small curated list when the speech provider is\nunreachable, so an empty result means something is wrong rather than that\nthere are no voices.","operationId":"list_preset_voices_voice_voice_library_presets_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Rows to return.","default":50,"title":"Limit"},"description":"Rows to return."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/call-results/inbound":{"get":{"tags":["Voice"],"summary":"Inbound call results","description":"Completed INBOUND calls, with summary, sentiment and disposition.\n\nThe inbound counterpart to the dialer history in `/voice/dialer/calls`.\nUse `/voice/call-results/search` for anything needing filters or paging.","operationId":"list_inbound_call_results_voice_call_results_inbound_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/call-results/campaigns":{"get":{"tags":["Voice"],"summary":"Campaign ids that have at least one call","description":"The valid filter values for `/voice/call-results/search`.\n\nBoth campaign id spaces are returned - sequencer and campaign builder -\nbecause a call can be attributed through either and they do not overlap.","operationId":"list_call_result_campaigns_voice_call_results_campaigns_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/call-results/search":{"post":{"tags":["Voice"],"summary":"Search call results","description":"READ-ONLY. A POST because the filter set is too wide for a query string.\n\nTiered `read` by an explicit entry in `READ_ONLY_POST_ROUTES`, the same\ncall already made for `POST /analytics/dialer/grading/search` - otherwise a\nPOST derives `write` and a read-only key could not search its own call\nhistory.\n\n`org_id` is stripped from the body and pinned from the key.","operationId":"search_call_results_voice_call_results_search_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Filters: `call_type`, `dispositions`, `campaign_ids`, `campaign_builder_campaign_ids`, `step_ids`, `mode` (`ai` | `dialer`), `search`, `updated_after`, `updated_before`, `sort_by`, `sort_order`, `page`, `page_size` (max 100).","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/video-recordings":{"get":{"tags":["Voice"],"summary":"List video recordings","description":"Recordings held for the organisation, without their transcripts.\n\n`user_id` here is the RECORDING'S SUBJECT, not the API caller - voice uses\nit for whoever the video is of. Fetch one recording to get its transcript.","operationId":"list_video_recordings_voice_video_recordings_get","parameters":[{"name":"user_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only recordings for this subject (candidate, employee, ...).","title":"User Id"},"description":"Only recordings for this subject (candidate, employee, ...)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Voice"],"summary":"Delete every recording for one subject","description":"Delete all of one subject's recordings and transcripts. NOT REVERSIBLE.\n\n`user_id` is REQUIRED so this can never be an accidental org-wide wipe.","operationId":"bulk_delete_video_recordings_voice_video_recordings_delete","parameters":[{"name":"user_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"description":"Whose recordings to delete. REQUIRED - there is no org-wide delete by omission.","title":"User Id"},"description":"Whose recordings to delete. REQUIRED - there is no org-wide delete by omission."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/video-recordings/{video_id}":{"get":{"tags":["Voice"],"summary":"Get a video recording with its transcript","description":"Full detail including the transcript. The list route omits it on purpose.","operationId":"get_video_recording_voice_video_recordings__video_id__get","parameters":[{"name":"video_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Recording id.","title":"Video Id"},"description":"Recording id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Voice"],"summary":"Delete one video recording","description":"Delete the recording and its transcript. NOT REVERSIBLE.","operationId":"delete_video_recording_voice_video_recordings__video_id__delete","parameters":[{"name":"video_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Recording id.","title":"Video Id"},"description":"Recording id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/video-recordings/{video_id}/url":{"get":{"tags":["Voice"],"summary":"Get a temporary playback URL for a recording","description":"A PRE-SIGNED URL, not the video.\n\nANYONE WITH THE URL CAN WATCH IT until it expires - it carries no further\nauthentication. Ask for the shortest expiry that works.","operationId":"get_video_recording_url_voice_video_recordings__video_id__url_get","parameters":[{"name":"video_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Recording id.","title":"Video Id"},"description":"Recording id."},{"name":"expiration","in":"query","required":false,"schema":{"type":"integer","maximum":86400,"minimum":60,"description":"How long the URL stays valid, in seconds.","default":3600,"title":"Expiration"},"description":"How long the URL stays valid, in seconds."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/chats/search":{"post":{"tags":["Voice"],"summary":"Search web-chat conversations","description":"READ-ONLY. A POST because the filter set is too wide for a query string.\n\nThe ORGANISATION's view of its web-chat conversations. Voice's own model\naccepts either a `user_id` or an `org_id`; the org is pinned from the key\nhere, so a caller always gets their own conversations and `user_id` can\nonly narrow within them.\n\nTiered `read` by an explicit `READ_ONLY_POST_ROUTES` entry - see\n`/voice/call-results/search` for the same reasoning.","operationId":"search_chats_voice_chats_search_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Filters: `limit` (max 200), `offset`, `ids`, `search` (chat name), `updated_after`, `updated_before`, `sort_by`, `sort_order`, and `user_id` to narrow to one visitor.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/workflow-connections":{"get":{"tags":["Voice"],"summary":"List the approved external destinations","description":"The destinations the organisation's workflows may reach: `items[]` with `destination_id`, `kind`, `value`, `enabled`.","operationId":"list_workflow_connections_voice_workflow_connections_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"post":{"tags":["Voice"],"summary":"Approve an external destination","description":"Allow the organisation's workflows to reach one destination. Org admin only.\n\n`value` is an exact host (`api.hubspot.com`), `.hubspot.com` for its subdomains, or `stdio:<command>` for a local MCP\ncommand. 400 when it is already approved. Whether workflows are actually held to the list is a platform setting: see\n`GET /voice/workflow-connections/enforcement`.","operationId":"approve_workflow_connection_voice_workflow_connections_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkflowConnectionCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/workflow-connections/enforcement":{"get":{"tags":["Voice"],"summary":"Whether the allowlist is enforced","description":"`enforced: true` when a workflow call to a destination that is not on the list is BLOCKED, `false` while it is only logged.\n\nA platform setting, not an organisation one. Org admin only, like the rest of the allowlist.","operationId":"get_workflow_connection_enforcement_voice_workflow_connections_enforcement_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/workflow-connections/{destination_id}":{"patch":{"tags":["Voice"],"summary":"Enable, disable or re-describe a destination","description":"Disable a destination to REVOKE it without losing the record; enable it to approve it again. Org admin only.","operationId":"update_workflow_connection_voice_workflow_connections__destination_id__patch","parameters":[{"name":"destination_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Destination id from the list.","title":"Destination Id"},"description":"Destination id from the list."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkflowConnectionUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Voice"],"summary":"Remove an approved destination","description":"Remove a destination from the allowlist. Workflows that call it afterwards are blocked while enforcement is on.","operationId":"revoke_workflow_connection_voice_workflow_connections__destination_id__delete","parameters":[{"name":"destination_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Destination id from the list.","title":"Destination Id"},"description":"Destination id from the list."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/campaigns/templates":{"get":{"tags":["Voice"],"summary":"Generate a campaign template for a company","description":"THIS COSTS CREDITS. Builds a multi-step campaign from a website.\n\nReturns the steps with their prompts, waits and channels - a starting\nsequence, not a saved one. Nothing is created in the campaign builder by\ncalling this.","operationId":"generate_campaign_template_voice_campaigns_templates_get","parameters":[{"name":"customer_url","in":"query","required":true,"schema":{"type":"string","description":"The company website to work from.","title":"Customer Url"},"description":"The company website to work from."},{"name":"type_campaign","in":"query","required":false,"schema":{"type":"string","description":"Which campaign shape to build.","default":"AI ICP Campaign","title":"Type Campaign"},"description":"Which campaign shape to build."},{"name":"run_async","in":"query","required":false,"schema":{"type":"boolean","description":"True returns a job id immediately (202) instead of waiting. Poll `GET /voice/jobs/{job_id}` for the result.","default":false,"title":"Run Async"},"description":"True returns a job id immediately (202) instead of waiting. Poll `GET /voice/jobs/{job_id}` for the result."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/campaigns/email-templates":{"get":{"tags":["Voice"],"summary":"Generate campaign email templates","description":"THIS COSTS CREDITS. Email templates from the org's own knowledge.\n\nGeneric templates for the organisation, not personalised to a contact -\n`POST /voice/campaigns/emails` is the per-contact version.","operationId":"generate_campaign_emails_voice_campaigns_email_templates_get","parameters":[{"name":"agent_name","in":"query","required":false,"schema":{"type":"string","description":"Whose voice to write in.","default":"default-agent","title":"Agent Name"},"description":"Whose voice to write in."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/campaigns/call-scripts":{"get":{"tags":["Voice"],"summary":"Generate campaign call scripts","description":"THIS COSTS CREDITS. Call scripts from the org's own knowledge.","operationId":"generate_campaign_call_scripts_voice_campaigns_call_scripts_get","parameters":[{"name":"agent_name","in":"query","required":false,"schema":{"type":"string","description":"Whose voice to write in.","default":"default-agent","title":"Agent Name"},"description":"Whose voice to write in."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"},"post":{"tags":["Voice"],"summary":"Generate one personalised call script","description":"THIS COSTS CREDITS. A script for one contact. Places no call.","operationId":"generate_campaign_call_script_voice_campaigns_call_scripts_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Contact and campaign context.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/campaigns/email-models":{"get":{"tags":["Voice"],"summary":"Models available for email generation","description":"The valid `model` values for the generation routes. Free, and a read.","operationId":"list_campaign_email_models_voice_campaigns_email_models_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/campaigns/email-estimate":{"post":{"tags":["Voice"],"summary":"Estimate what generating an email would cost","description":"FREE. Reports the token cost and GENERATES NOTHING.\n\nThe only way to learn what `POST /voice/campaigns/emails` will cost before\nspending it, which is exactly why it must not be gated behind the spend\npermission. It is in `READ_ONLY_POST_ROUTES` for that reason - the\n`/estimate` billable marker catches it by name and gets it backwards.","operationId":"estimate_campaign_email_voice_campaigns_email_estimate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"The same body `POST /voice/campaigns/emails` takes.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/campaigns/emails":{"post":{"tags":["Voice"],"summary":"Generate one personalised email","description":"THIS COSTS CREDITS, per call. Generates, it does not send.\n\nNothing reaches a recipient here - the result is text for you to put into a\nsequence or send yourself.","operationId":"generate_campaign_email_voice_campaigns_emails_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Contact and campaign context. Call `POST /voice/campaigns/email-estimate` with the same body first to learn the cost.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/campaigns/email-enhancements":{"post":{"tags":["Voice"],"summary":"Rewrite a generated email against an instruction","description":"THIS COSTS CREDITS. A second pass over a draft, not a fresh generation.","operationId":"enhance_campaign_email_voice_campaigns_email_enhancements_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"The draft plus the instruction. A user instruction is REQUIRED - voice rejects the call without one rather than guessing.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/campaigns/email-spintax":{"post":{"tags":["Voice"],"summary":"Turn an email into spintax","description":"THIS COSTS CREDITS. ONE-TIME generation, not a live variation engine.\n\nRewrites a manually written email into `{{a|b}}` spintax so each send picks\na different phrasing. The spintax is produced once; expanding it later\ncosts nothing.","operationId":"generate_email_spintax_voice_campaigns_email_spintax_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"The email to rewrite.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/campaigns/linkedin-messages":{"post":{"tags":["Voice"],"summary":"Generate a LinkedIn message","description":"THIS COSTS CREDITS. Connection request, DM or InMail. SENDS NOTHING.\n\nOnly a connection request has a length limit worth worrying about; the\nresult carries `subject` for InMail and null otherwise.","operationId":"generate_linkedin_message_voice_campaigns_linkedin_messages_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Contact context, plus which kind of message to write.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/campaigns/voicemails":{"post":{"tags":["Voice"],"summary":"Generate a personalised voicemail script","description":"THIS COSTS CREDITS. Returns TEXT - it does not record or drop a voicemail.\n\nDropping a voicemail on a live call is a dialer operation and is not on\nthis router.","operationId":"generate_personalised_voicemail_voice_campaigns_voicemails_post","parameters":[{"name":"campaign_type","in":"query","required":false,"schema":{"type":"string","description":"Which campaign shape to write for.","default":"default","title":"Campaign Type"},"description":"Which campaign shape to write for."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Contact context.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/campaigns/memory":{"post":{"tags":["Voice"],"summary":"Record past campaign history for a contact","description":"Stores history so later generation knows what was already said.\n\nA plain write - it calls no model and spends nothing, which is why it is in\n`WRITE_OVERRIDE_ROUTES` rather than inheriting this router's billable\nbucket. What it costs is the NEXT generation being better informed.","operationId":"store_campaign_memory_voice_campaigns_memory_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Body_store_campaign_memory_voice_campaigns_memory_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/campaigns/past-conversation":{"get":{"tags":["Voice"],"summary":"Summary of prior conversation with one contact","description":"The summary generation reads before writing to someone again.","operationId":"get_past_conversation_voice_campaigns_past_conversation_get","parameters":[{"name":"contact_id","in":"query","required":true,"schema":{"type":"string","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/campaigns/past-conversations":{"get":{"tags":["Voice"],"summary":"All recorded conversation history for one contact","description":"The full history rather than the single summary beside it.\n\nNote the contact id is an INTEGER here and a string on\n`/campaigns/past-conversation`. That asymmetry is voice's and is mirrored\nrather than papered over - narrowing one would 422 ids the other accepts.","operationId":"list_past_conversations_voice_campaigns_past_conversations_get","parameters":[{"name":"contact_id","in":"query","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/campaigns/onboarding/messages":{"post":{"tags":["Voice"],"summary":"Talk to the campaign onboarding agent","description":"THIS COSTS CREDITS, per turn. Returns the reply and the updated state.\n\nA stateful conversation: create a thread first, then send messages into it.","operationId":"send_onboarding_message_voice_campaigns_onboarding_messages_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"The message plus the thread it belongs to.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/campaigns/onboarding/threads":{"get":{"tags":["Voice"],"summary":"List onboarding conversation threads","description":"Thread ids, titles, and whether each one produced a campaign.","operationId":"list_onboarding_threads_voice_campaigns_onboarding_threads_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"post":{"tags":["Voice"],"summary":"Start an onboarding conversation thread","description":"Creates an EMPTY thread and returns its id. Calls no model.\n\nA plain write, which is why it is in `WRITE_OVERRIDE_ROUTES` - the spend\nstarts when you send a message into it.","operationId":"create_onboarding_thread_voice_campaigns_onboarding_threads_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Optional thread metadata, e.g. a title.","title":"Payload"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Voice"],"summary":"Delete an onboarding thread","description":"Deletes the thread and its messages. NOT REVERSIBLE.\n\nA campaign the thread already produced is NOT deleted - it is a separate\nrecord and survives.\n\nThe thread id is a query parameter rather than a path segment because\nvoice's own delete takes it in the body, and a DELETE with a required body\nis not a shape to publish.","operationId":"delete_onboarding_thread_voice_campaigns_onboarding_threads_delete","parameters":[{"name":"thread_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"description":"The thread to delete.","title":"Thread Id"},"description":"The thread to delete."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/campaigns/onboarding/threads/{thread_id}":{"get":{"tags":["Voice"],"summary":"Read an onboarding thread's messages","description":"Every message in the thread, oldest first.\n\nVoice puts the organisation in the PATH here. It is not in this one: the\nonly correct value is the one on the key.","operationId":"get_onboarding_thread_voice_campaigns_onboarding_threads__thread_id__get","parameters":[{"name":"thread_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Thread id.","title":"Thread Id"},"description":"Thread id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/campaigns/onboarding/threads/actions":{"post":{"tags":["Voice"],"summary":"Run an action the onboarding agent proposed","description":"THIS CREATES REAL RECORDS. The confirmation step, not a preview.\n\nThe onboarding conversation proposes things; this is what makes one happen\n- creating an ICP campaign, for example. Read the agent's last message\nbefore calling it.","operationId":"run_onboarding_thread_action_voice_campaigns_onboarding_threads_actions_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"The thread and which proposed action to execute.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/research/company":{"post":{"tags":["Voice"],"summary":"Deep-research a company","description":"THIS COSTS MONEY. Verification, market analysis and news, from several\npaid providers.\n\nCost scales with `max_sources` and `research_depth`, and voice guards it\nwith its EXPENSIVE rate limit - roughly five calls a minute. A batch\noperation, not something to call per row.","operationId":"research_company_voice_research_company_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Body_research_company_voice_research_company_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/research/org-chart":{"post":{"tags":["Voice"],"summary":"Research a company's org chart","description":"THIS COSTS MONEY. Who reports to whom, from several paid providers.\n\n`include_contact_info: true` additionally resolves emails and phone\nnumbers, which is the most expensive part. Set it false when you only need\nthe shape of the organisation.","operationId":"research_org_chart_voice_research_org_chart_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Body_research_org_chart_voice_research_org_chart_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/research/business-data":{"get":{"tags":["Voice"],"summary":"Business profile for a company website","description":"THIS COSTS CREDITS. Scrapes and summarises the company behind a URL.","operationId":"research_business_data_voice_research_business_data_get","parameters":[{"name":"customer_url","in":"query","required":true,"schema":{"type":"string","description":"The company website to work from.","title":"Customer Url"},"description":"The company website to work from."},{"name":"run_async","in":"query","required":false,"schema":{"type":"boolean","description":"True returns a job id immediately (202) instead of waiting. Poll `GET /voice/jobs/{job_id}` for the result.","default":false,"title":"Run Async"},"description":"True returns a job id immediately (202) instead of waiting. Poll `GET /voice/jobs/{job_id}` for the result."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/research/competitors":{"get":{"tags":["Voice"],"summary":"Competitors of a company","description":"THIS COSTS CREDITS. Who else the company is up against.","operationId":"research_competitors_voice_research_competitors_get","parameters":[{"name":"customer_url","in":"query","required":true,"schema":{"type":"string","description":"The company website to work from.","title":"Customer Url"},"description":"The company website to work from."},{"name":"run_async","in":"query","required":false,"schema":{"type":"boolean","description":"True returns a job id immediately (202) instead of waiting. Poll `GET /voice/jobs/{job_id}` for the result.","default":false,"title":"Run Async"},"description":"True returns a job id immediately (202) instead of waiting. Poll `GET /voice/jobs/{job_id}` for the result."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/research/keywords":{"get":{"tags":["Voice"],"summary":"Search keywords and paid-search data for a company","description":"THIS COSTS CREDITS. Keywords with search-marketing volume attached.","operationId":"research_keywords_voice_research_keywords_get","parameters":[{"name":"customer_url","in":"query","required":true,"schema":{"type":"string","description":"The company website to work from.","title":"Customer Url"},"description":"The company website to work from."},{"name":"run_async","in":"query","required":false,"schema":{"type":"boolean","description":"True returns a job id immediately (202) instead of waiting. Poll `GET /voice/jobs/{job_id}` for the result.","default":false,"title":"Run Async"},"description":"True returns a job id immediately (202) instead of waiting. Poll `GET /voice/jobs/{job_id}` for the result."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/research/faq":{"get":{"tags":["Voice"],"summary":"FAQs extracted from a company website","description":"THIS COSTS CREDITS. Question-and-answer pairs an agent can reuse.\n\nA good first source for `/voice/company-knowledge`'s `faqs` field.","operationId":"research_faq_voice_research_faq_get","parameters":[{"name":"customer_url","in":"query","required":true,"schema":{"type":"string","description":"The company website to work from.","title":"Customer Url"},"description":"The company website to work from."},{"name":"run_async","in":"query","required":false,"schema":{"type":"boolean","description":"True returns a job id immediately (202) instead of waiting. Poll `GET /voice/jobs/{job_id}` for the result.","default":false,"title":"Run Async"},"description":"True returns a job id immediately (202) instead of waiting. Poll `GET /voice/jobs/{job_id}` for the result."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/research/prospect-data":{"post":{"tags":["Voice"],"summary":"Extract prospect data from a form submission","description":"THIS COSTS CREDITS. Turns free-text form answers into structured fields.","operationId":"research_prospect_data_voice_research_prospect_data_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"The submitted form fields.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/research/prospect-company":{"get":{"tags":["Voice"],"summary":"Competitor and signal profile for a prospect's company","description":"MAY COST CREDITS. Served from the database when already researched.\n\nA GET that is not free: voice answers from storage when it can and\nresearches when it cannot, so the cost of a given call depends on whether\nthat company has been seen before. Tiered with the rest of this router\nrather than as a plain read, because the expensive branch is the one that\nmatters.","operationId":"research_prospect_company_voice_research_prospect_company_get","parameters":[{"name":"company_name","in":"query","required":true,"schema":{"type":"string","description":"Prospect's company name.","title":"Company Name"},"description":"Prospect's company name."},{"name":"company_website","in":"query","required":true,"schema":{"type":"string","description":"Prospect's company website.","title":"Company Website"},"description":"Prospect's company website."},{"name":"company_description","in":"query","required":false,"schema":{"type":"string","description":"What the company does, if known.","default":"","title":"Company Description"},"description":"What the company does, if known."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/research/prospect-profile":{"post":{"tags":["Voice"],"summary":"Generate a full prospect profile","description":"THIS COSTS CREDITS. Background, skills, experience and competitors.","operationId":"research_prospect_profile_voice_research_prospect_profile_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"What is already known about the prospect.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/icp/queries":{"post":{"tags":["Voice"],"summary":"Generate ICP and TAM query definitions from a website","description":"THIS COSTS CREDITS. Seniority, industry, headcount and revenue filters.\n\nReturns both an ICP (who to sell to) and a TAM (the wider addressable set),\nready to drive a prospecting search. `persist: false` makes it a pure\ngeneration with nothing written.","operationId":"generate_icp_queries_voice_icp_queries_post","parameters":[{"name":"customer_url","in":"query","required":true,"schema":{"type":"string","description":"The company to build an ICP for.","title":"Customer Url"},"description":"The company to build an ICP for."},{"name":"run_async","in":"query","required":false,"schema":{"type":"boolean","description":"True returns a job id immediately (202) instead of waiting. Poll `GET /voice/jobs/{job_id}` for the result.","default":false,"title":"Run Async"},"description":"True returns a job id immediately (202) instead of waiting. Poll `GET /voice/jobs/{job_id}` for the result."},{"name":"persist","in":"query","required":false,"schema":{"type":"boolean","description":"True stores the generated ICP against the org. False returns it only.","default":true,"title":"Persist"},"description":"True stores the generated ICP against the org. False returns it only."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/topics/classify":{"post":{"tags":["Voice"],"summary":"Classify URLs into intent topics","description":"THIS COSTS CREDITS, per URL. Returns the five most probable topics each.\n\nThe same topic vocabulary the intent surface uses, applied to pages you\nname rather than pages visitors were seen on.","operationId":"classify_topics_voice_topics_classify_post","parameters":[{"name":"run_async","in":"query","required":false,"schema":{"type":"boolean","description":"Defaults TRUE here, matching voice: a batch of URLs is slow enough that a synchronous call usually times out. Poll `GET /voice/jobs/{job_id}`.","default":true,"title":"Run Async"},"description":"Defaults TRUE here, matching voice: a batch of URLs is slow enough that a synchronous call usually times out. Poll `GET /voice/jobs/{job_id}`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"The URLs to classify.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/worksheets/calculate":{"post":{"tags":["Voice"],"summary":"Fill worksheet cells with AI answers","description":"THIS COSTS CREDITS, PER CELL. Cost scales with the size of the request.\n\nA spreadsheet-shaped batch: each cell is its own model call, so a hundred\nrows is a hundred charges. Run it asynchronously and poll the job for\nanything but a handful of cells.","operationId":"calculate_worksheet_voice_worksheets_calculate_post","parameters":[{"name":"run_async","in":"query","required":false,"schema":{"type":"boolean","description":"True returns a job id immediately (202) instead of waiting. Poll `GET /voice/jobs/{job_id}` for the result.","default":false,"title":"Run Async"},"description":"True returns a job id immediately (202) instead of waiting. Poll `GET /voice/jobs/{job_id}` for the result."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"The table, and which cells to fill.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/jobs/{job_id}":{"get":{"tags":["Voice"],"summary":"Poll an async job","description":"Status and, once finished, the result.\n\nThis is the published answer to every `async=true` route here, and the\nreason `callback_url` is not published: polling needs no inbound URL of\nours pointed at an address a caller chose.","operationId":"get_job_voice_jobs__job_id__get","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Job id from a 202 response.","title":"Job Id"},"description":"Job id from a 202 response."},{"name":"queue","in":"query","required":false,"schema":{"type":"string","description":"Which queue the job was placed on.","default":"normal","title":"Queue"},"description":"Which queue the job was placed on."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Voice"],"summary":"Cancel an async job","description":"Cancel a queued job, or discard a finished one's result.\n\nWork ALREADY DONE is still charged - cancelling stops what has not started,\nit does not refund what has.","operationId":"delete_job_voice_jobs__job_id__delete","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Job id.","title":"Job Id"},"description":"Job id."},{"name":"queue","in":"query","required":false,"schema":{"type":"string","description":"Which queue the job was placed on.","default":"normal","title":"Queue"},"description":"Which queue the job was placed on."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/chat-agent/messages":{"post":{"tags":["Voice"],"summary":"Send a message to the chat agent","description":"THIS COSTS CREDITS, per turn. The agent may also RUN ITS SKILLS.\n\nNot just text generation: an agent with skills attached can decide to run\none while answering, which can reach outside graph8. See\n`POST /voice/agents/{agent_id}/skills` for what a given agent is allowed\nto do.","operationId":"send_chat_agent_message_voice_chat_agent_messages_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"The message, the agent to send it to, and the conversation.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/chat-agent/history":{"post":{"tags":["Voice"],"summary":"Read a chat agent conversation","description":"READ-ONLY. A POST because voice takes the selector as a body.\n\nIn `READ_ONLY_POST_ROUTES`: left in this router's billable bucket, a\nread-only key could not read its own chat history.","operationId":"get_chat_agent_history_voice_chat_agent_history_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Which conversation to read.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/chat-agent/conversations":{"post":{"tags":["Voice"],"summary":"List chat agent conversations","description":"READ-ONLY, despite the verb - voice takes the filter as a body.\n\nAlso in `READ_ONLY_POST_ROUTES`, for the same reason as the history route.","operationId":"list_chat_agent_conversations_voice_chat_agent_conversations_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Which agent's conversations, and any paging.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/chat-agent/conversations/{chat_id}/name":{"put":{"tags":["Voice"],"summary":"Rename a chat agent conversation","description":"A label change. Calls no model, so it is in `WRITE_OVERRIDE_ROUTES`.","operationId":"rename_chat_agent_conversation_voice_chat_agent_conversations__chat_id__name_put","parameters":[{"name":"chat_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Conversation id.","title":"Chat Id"},"description":"Conversation id."},{"name":"agent_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"description":"The agent that owns it.","title":"Agent Id"},"description":"The agent that owns it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Body_rename_chat_agent_conversation_voice_chat_agent_conversations__chat_id__name_put"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/chat-agent/conversations/{chat_id}":{"delete":{"tags":["Voice"],"summary":"Delete a chat agent conversation","description":"Delete the conversation and its messages. NOT REVERSIBLE.\n\nWhat the agent LEARNED from it may survive in memory - see\n`POST /voice/agents/{agent_id}/memory`. Deleting the transcript is not the\nsame as making the agent forget.","operationId":"delete_chat_agent_conversation_voice_chat_agent_conversations__chat_id__delete","parameters":[{"name":"chat_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Conversation id.","title":"Chat Id"},"description":"Conversation id."},{"name":"agent_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"description":"The agent that owns it.","title":"Agent Id"},"description":"The agent that owns it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/chat-agent/conversations/{chat_id}/transfer-to-human":{"post":{"tags":["Voice"],"summary":"Hand a chat agent conversation to a person","description":"Flags the conversation for human takeover and notifies the queue.\n\nCalls no model, so it is in `WRITE_OVERRIDE_ROUTES` rather than inheriting\nthis router's billable bucket. What it costs is someone's attention.","operationId":"transfer_chat_agent_conversation_voice_chat_agent_conversations__chat_id__transfer_to_human_post","parameters":[{"name":"chat_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Conversation id.","title":"Chat Id"},"description":"Conversation id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/receptionist/messages":{"post":{"tags":["Voice"],"summary":"Send a text message to the receptionist","description":"THIS COSTS CREDITS, per turn. The text channel of the receptionist.\n\nThe receptionist itself is configured at `POST /voice/agents/receptionist`.\nVoice rate-limits this route twice - per IP and as a burst - because it is\nreachable from a public widget; a server-to-server caller shares those\nlimits.","operationId":"send_receptionist_message_voice_receptionist_messages_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"The message and its conversation.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/email-agent/compose":{"post":{"tags":["Voice"],"summary":"Compose an email with the email agent","description":"THIS COSTS CREDITS. Writes, it does NOT send.\n\nRicher than `POST /voice/campaigns/emails`: the email agent retrieves from\nthe agent's collections and its memory of the contact, so it can refer to\nwhat was actually said before.","operationId":"compose_email_voice_email_agent_compose_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Who it is to, and what it is about.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/email-agent/draft-reply":{"post":{"tags":["Voice"],"summary":"Draft a reply to an email","description":"THIS COSTS CREDITS. Drafts a reply. NOTHING IS SENT.\n\nPublished as `draft-reply`, not `reply`. Two reasons, and they agree: it\nDRAFTS, so calling it `reply` would promise a send it does not perform;\nand `/reply` is an EXTERNAL_PATH_MARKER, so that spelling derived the\n`external` tier - overstating a route that reaches nobody, while\n`/email-agent/compose` beside it correctly derived `billable`. The name\nthat describes the behaviour is also the one that tiers it correctly.","operationId":"draft_email_reply_voice_email_agent_draft_reply_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"The email being replied to, plus context.","title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/phone-directory":{"get":{"tags":["Voice"],"summary":"The organisation's phone directory","description":"SPENDS NOTHING. Every directory entry, numbers resolved.\n\n`phone_number` is the stored override; `work_number` is the number\nassigned in the inventory; `effective_phone_number` is what a transfer\nwould dial. Inactive entries are included - this is the editable list.","operationId":"list_phone_directory_voice_phone_directory_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"post":{"tags":["Voice"],"summary":"Add a colleague to the directory","description":"SPENDS NOTHING. Adds an entry. The organisation is the key's; a body\nvalue is not accepted. Voice answers 400 with its own detail when the row\ncannot be inserted (for example a duplicate extension).","operationId":"create_phone_directory_entry_voice_phone_directory_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PhoneDirectoryEntryCreate"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/phone-directory/reachable":{"get":{"tags":["Voice"],"summary":"Colleagues who can be reached right now","description":"SPENDS NOTHING. Active colleagues with a dialable number and live engaged state.\n\nThe shape behind the receptionist's directory prompt, the Work Phone\ncolleague search and the in-call transfer picker: reachable first, then\nby name. `is_engaged` is read from the on-call tracker at request time.","operationId":"list_reachable_colleagues_voice_phone_directory_reachable_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/phone-directory/departments/{department}":{"get":{"tags":["Voice"],"summary":"One department's reachable members","description":"SPENDS NOTHING. The reachable shape filtered to one department.\n\nA caller asking \"who is in sales\" wants who can be reached, so this\nanswers the `/reachable` shape rather than raw rows.","operationId":"list_department_colleagues_voice_phone_directory_departments__department__get","parameters":[{"name":"department","in":"path","required":true,"schema":{"type":"string","description":"Department name; matched case-insensitively.","title":"Department"},"description":"Department name; matched case-insensitively."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/phone-directory/{entry_id}":{"put":{"tags":["Voice"],"summary":"Edit a directory entry","description":"SPENDS NOTHING. Partial update; omitted fields are untouched.\n\n404 when the entry does not exist OR belongs to another organisation -\nvoice deliberately answers both the same way so ids cannot be probed.","operationId":"update_phone_directory_entry_voice_phone_directory__entry_id__put","parameters":[{"name":"entry_id","in":"path","required":true,"schema":{"type":"integer","description":"Directory entry id.","title":"Entry Id"},"description":"Directory entry id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PhoneDirectoryEntryUpdate"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Voice"],"summary":"Remove a directory entry","description":"SPENDS NOTHING. Removes the entry; transfers to that extension stop\nresolving. Same 404 for \"missing\" and \"not yours\" as the update.","operationId":"delete_phone_directory_entry_voice_phone_directory__entry_id__delete","parameters":[{"name":"entry_id","in":"path","required":true,"schema":{"type":"integer","description":"Directory entry id.","title":"Entry Id"},"description":"Directory entry id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/agents/{agent_id}/test-cases":{"post":{"tags":["Voice"],"summary":"Save an evaluation case for an agent","description":"SPENDS NOTHING. Saves a named case: the user turn, its context, and the\nassertion the agent's resolved behaviour must satisfy.\n\n`created_by` defaults to the key's identity, since a server-to-server\ncall carries no request-context user for voice to fall back on.","operationId":"create_agent_test_case_voice_agents__agent_id__test_cases_post","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","description":"Voice agent id.","title":"Agent Id"},"description":"Voice agent id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentTestCaseCreate"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"get":{"tags":["Voice"],"summary":"The agent's saved evaluation cases","description":"SPENDS NOTHING. Every saved case for the agent, as `items`.","operationId":"list_agent_test_cases_voice_agents__agent_id__test_cases_get","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","description":"Voice agent id.","title":"Agent Id"},"description":"Voice agent id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/agents/{agent_id}/test-cases/{test_case_id}":{"put":{"tags":["Voice"],"summary":"Edit a saved case","description":"SPENDS NOTHING. Partial update: omitted fields are untouched, an\nexplicit null clears a nullable one (`input_context`, `expected_output`,\n`assertion_config`).","operationId":"update_agent_test_case_voice_agents__agent_id__test_cases__test_case_id__put","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","description":"Voice agent id.","title":"Agent Id"},"description":"Voice agent id."},{"name":"test_case_id","in":"path","required":true,"schema":{"type":"string","description":"Saved test case id.","title":"Test Case Id"},"description":"Saved test case id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentTestCaseUpdate"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Voice"],"summary":"Delete a saved case","description":"SPENDS NOTHING. Deletes the case. Its historical runs keep their\n`test_case_id` so old regression summaries stay readable.","operationId":"delete_agent_test_case_voice_agents__agent_id__test_cases__test_case_id__delete","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","description":"Voice agent id.","title":"Agent Id"},"description":"Voice agent id."},{"name":"test_case_id","in":"path","required":true,"schema":{"type":"string","description":"Saved test case id.","title":"Test Case Id"},"description":"Saved test case id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/agents/{agent_id}/test":{"post":{"tags":["Voice"],"summary":"Dry-run one case, saved or ad-hoc","description":"SPENDS NOTHING. One dry run, from a saved case (`test_case_id`) or an\nad-hoc input (`input_message`), never both.\n\nReturns the run row with the composed preview: the instruction stack the\nagent would receive, the tools it could reach for and the grounding it\ncould cite, judged against the assertion. No model call, no call placed,\nno message sent. `triggered_by` defaults to the key's identity.","operationId":"run_agent_test_voice_agents__agent_id__test_post","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","description":"Voice agent id.","title":"Agent Id"},"description":"Voice agent id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentTestRun"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/agents/{agent_id}/test/run-all":{"post":{"tags":["Voice"],"summary":"Regression run: every saved case, plus the activation gate","description":"SPENDS NOTHING. Runs every saved case server-side, one config hash,\npass/fail per case, and returns the activation `gate` recomputed from\nthese fresh runs - so a client can run-then-decide in one round trip.\nStill a dry run: no model, no call, no send.","operationId":"run_all_agent_tests_voice_agents__agent_id__test_run_all_post","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","description":"Voice agent id.","title":"Agent Id"},"description":"Voice agent id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/AgentRegressionRun"},{"type":"null"}],"title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/agents/{agent_id}/test-runs":{"get":{"tags":["Voice"],"summary":"Run history, newest first","description":"SPENDS NOTHING. Past runs as `items`. Reading also lets voice apply its\nretention caps, so an organisation that only reads still converges.","operationId":"list_agent_test_runs_voice_agents__agent_id__test_runs_get","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","description":"Voice agent id.","title":"Agent Id"},"description":"Voice agent id."},{"name":"test_case_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only runs of this saved case.","title":"Test Case Id"},"description":"Only runs of this saved case."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"include_output","in":"query","required":false,"schema":{"type":"boolean","description":"Include the stored previews (heavier).","default":false,"title":"Include Output"},"description":"Include the stored previews (heavier)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/agents/{agent_id}/test-suite-status":{"get":{"tags":["Voice"],"summary":"The activation gate: does the saved suite vouch for this config?","description":"SPENDS NOTHING. Read-only: reports on runs that already exist rather\nthan firing a sweep, so it can be polled. `status` is `passing`,\n`failing` or `none`; run `test/run-all` first to refresh it.","operationId":"get_agent_test_suite_status_voice_agents__agent_id__test_suite_status_get","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","description":"Voice agent id.","title":"Agent Id"},"description":"Voice agent id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}/files/upload":{"post":{"tags":["Voice"],"summary":"Upload one file into a collection","description":"SPENDS CREDITS. Stores the file in the collection and indexes it for\nretrieval; the indexing embeds the text against a paid model, which is\nwhy this is `billable` like `reindex` and `paste-text`.\n\nVoice extracts text from PDF, DOCX, spreadsheets, HTML and plain text;\nan unsupported type is voice's own 4xx, forwarded.","operationId":"upload_collection_file_voice_collections__collection_id__files_upload_post","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_collection_file_voice_collections__collection_id__files_upload_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}/files/upload-multiple":{"post":{"tags":["Voice"],"summary":"Upload several files into a collection","description":"SPENDS CREDITS. Same as the single upload, for a batch. Voice answers\nper file which were stored and indexed and which failed; read it rather\nthan assuming every file landed.","operationId":"upload_collection_files_voice_collections__collection_id__files_upload_multiple_post","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_collection_files_voice_collections__collection_id__files_upload_multiple_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/knowledge-base/files/upload":{"post":{"tags":["Voice"],"summary":"Upload a file to the org-wide knowledge base","description":"SPENDS CREDITS. Stores the file in the org-wide knowledge base agents\nanswer from and refreshes the index, which embeds against a paid model.\n`filename` is the stored name, and the one `.../files/download` takes.","operationId":"upload_knowledge_base_file_voice_knowledge_base_files_upload_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_knowledge_base_file_voice_knowledge_base_files_upload_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/knowledge-base/files/download":{"get":{"tags":["Voice"],"summary":"Download a knowledge-base file","description":"SPENDS NOTHING. The file's bytes, streamed, with voice's\n`Content-Disposition`. Not enveloped: bytes are bytes.","operationId":"download_knowledge_base_file_voice_knowledge_base_files_download_get","parameters":[{"name":"filename","in":"query","required":true,"schema":{"type":"string","minLength":1,"description":"The stored name, as listed.","title":"Filename"},"description":"The stored name, as listed."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/agents/{agent_id}/documents/upload":{"post":{"tags":["Voice"],"summary":"Upload documents into an agent's own vector store","description":"SPENDS CREDITS. Extracts the text and embeds it into the agent's private\nvector store against a paid model. Voice answers which documents were\nindexed and which failed. 404 when the agent is not this organisation's.","operationId":"upload_agent_documents_voice_agents__agent_id__documents_upload_post","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","description":"Voice agent id.","title":"Agent Id"},"description":"Voice agent id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_agent_documents_voice_agents__agent_id__documents_upload_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/video-recordings/upload":{"post":{"tags":["Voice"],"summary":"Upload a video recording for transcription","description":"SPENDS CREDITS. Stores the video and transcribes it, which runs a paid\nspeech model over the whole recording. Voice checks the container type\n(415 otherwise). Stored under `org / user_id / folder_path / filename`.","operationId":"upload_video_recording_voice_video_recordings_upload_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_video_recording_voice_video_recordings_upload_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/call-flow-examples/transcribe":{"post":{"tags":["Voice"],"summary":"Transcribe a recorded call into the org's call-flow example","description":"SPENDS CREDITS. Transcribes the recording with a paid speech model, has a\npaid LLM turn the transcript into a call-flow script, and SAVES it as the\norg's call-flow example (replacing any previous one), which voice agents\ndraw on when they write call scripts. The generated script is returned\nunder `result`. Voice checks the audio type (415 otherwise).","operationId":"transcribe_call_flow_example_voice_call_flow_examples_transcribe_post","parameters":[{"name":"language","in":"query","required":false,"schema":{"type":"string","minLength":2,"maxLength":16,"description":"Language spoken in the recording.","default":"en","title":"Language"},"description":"Language spoken in the recording."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_transcribe_call_flow_example_voice_call_flow_examples_transcribe_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/voice-library/voices":{"get":{"tags":["Voice"],"summary":"The voices this organisation has cloned","description":"SPENDS NOTHING. The org's cloned voices, newest first. Presets are\n`GET /voice/voice-library/presets`; this is what the org made itself.","operationId":"list_cloned_voices_voice_voice_library_voices_get","parameters":[{"name":"created_by_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only voices cloned by this user.","title":"Created By Email"},"description":"Only voices cloned by this user."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"post":{"tags":["Voice"],"summary":"Clone a voice from a short audio sample","description":"SPENDS CREDITS. Sends the sample to the voice provider and registers the\ncloned voice for the organisation; agents can then be assigned it. Voice\nrefuses anything but `.wav` / `.mp3` and anything over ten seconds (400).","operationId":"clone_voice_voice_voice_library_voices_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_clone_voice_voice_voice_library_voices_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/voice-library/onboarding-voice":{"post":{"tags":["Voice"],"summary":"Replace the organisation's onboarding voice","description":"SPENDS CREDITS. Clones the sample as the organisation's onboarding\nvoice, REPLACING the previous one (voice deletes it at the provider\nfirst). There is one per organisation, which is why this is not a\ncollection.","operationId":"set_onboarding_voice_voice_voice_library_onboarding_voice_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_set_onboarding_voice_voice_voice_library_onboarding_voice_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/twins/files/download":{"get":{"tags":["Voice"],"summary":"Download a twin's stored file","description":"SPENDS NOTHING. The file's bytes, streamed. Voice checks that the key\nbelongs to this organisation (`twins/{org}/...`) before serving it; a key\nfrom another organisation is voice's own 403, forwarded.","operationId":"download_twin_file_voice_twins_files_download_get","parameters":[{"name":"s3_key","in":"query","required":true,"schema":{"type":"string","minLength":1,"description":"The stored key, as returned on the twin.","title":"S3 Key"},"description":"The stored key, as returned on the twin."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/calls/{call_id}/recording":{"get":{"tags":["Voice"],"summary":"Stream a call's recording","description":"SPENDS NOTHING. The recording's bytes (`audio/mpeg` unless stored\notherwise) with voice's `Content-Disposition`. 425 with `Retry-After`\nwhile the recording is still being finalised; 404 for a call that is not\nthis organisation's.","operationId":"download_call_recording_voice_calls__call_id__recording_get","parameters":[{"name":"call_id","in":"path","required":true,"schema":{"type":"string","description":"Call id.","title":"Call Id"},"description":"Call id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/calls/{call_id}/historical-recording":{"get":{"tags":["Voice"],"summary":"Recover an old recording by its activity","description":"SPENDS NOTHING. For a recording whose canonical call row was lost:\nvoice resolves it through the tenant's activity record instead. Streams\nthe bytes; 404 when nothing matches.","operationId":"download_historical_call_recording_voice_calls__call_id__historical_recording_get","parameters":[{"name":"call_id","in":"path","required":true,"schema":{"type":"string","description":"Call id.","title":"Call Id"},"description":"Call id."},{"name":"activity_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"description":"The activity that proves the recording belongs to this call.","title":"Activity Id"},"description":"The activity that proves the recording belongs to this call."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/dialer/sessions":{"get":{"tags":["Voice"],"summary":"List parallel dialer sessions","description":"List parallel dialer sessions for the authenticated org.\n\nForwards to the voice service's ``GET /api/parallel-calls/sessions``\nendpoint with ``org_id`` pinned to the API key's org. All filtering /\npaging arguments map 1:1 to the upstream contract.","operationId":"list_dialer_sessions_voice_dialer_sessions_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (1-indexed).","default":1,"title":"Page"},"description":"Page number (1-indexed)."},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Sessions per page (max 200).","default":50,"title":"Page Size"},"description":"Sessions per page (max 200)."},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated session statuses (e.g. \"ACTIVE,PAUSED\").","title":"Status"},"description":"Comma-separated session statuses (e.g. \"ACTIVE,PAUSED\")."},{"name":"user_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by SDR email (substring).","title":"User Email"},"description":"Filter by SDR email (substring)."},{"name":"name","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by session name (substring).","title":"Name"},"description":"Filter by session name (substring)."},{"name":"campaign_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by campaign id (substring).","title":"Campaign Id"},"description":"Filter by campaign id (substring)."},{"name":"list_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by list id stored in session metadata.","title":"List Id"},"description":"Filter by list id stored in session metadata."},{"name":"list_name","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by list title (substring).","title":"List Name"},"description":"Filter by list title (substring)."},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO timestamp - sessions created on/after.","title":"Date From"},"description":"ISO timestamp - sessions created on/after."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO timestamp - sessions created on/before.","title":"Date To"},"description":"ISO timestamp - sessions created on/before."},{"name":"sort_by","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Column to sort on (e.g. \"created_at\", \"updated_at\", \"total_calls\").","title":"Sort By"},"description":"Column to sort on (e.g. \"created_at\", \"updated_at\", \"total_calls\")."},{"name":"sort_order","in":"query","required":false,"schema":{"type":"string","description":"\"asc\" or \"desc\". Defaults to desc.","default":"desc","title":"Sort Order"},"description":"\"asc\" or \"desc\". Defaults to desc."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerSessionsListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"post":{"tags":["Voice"],"summary":"Create a parallel-dialer session in PAUSED state","description":"Create a new parallel-dialer session bound to the caller's org.\n\nThe session is created in ``PAUSED`` state - no calls are placed\nuntil the SDR opens the dialer UI and joins the Twilio conference.\nThe chat caller can then use ``PATCH /voice/dialer/sessions/{id}/status``\nor any frontend control to pause / resume / stop later.\n\nOrg and user are pinned server-side from the API key. The caller\ncannot override them.","operationId":"create_dialer_session_voice_dialer_sessions_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DialerSessionCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerSessionCreateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/dialer/stats":{"get":{"tags":["Voice"],"summary":"Parallel dialer analytics report","description":"Return aggregated dialer metrics for the caller's org.\n\nOrg scoping is enforced server-side: the voice service accepts a\n``user_email`` filter but the org is always pinned to the API key.","operationId":"get_dialer_stats_voice_dialer_stats_get","parameters":[{"name":"session_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter to a single session.","title":"Session Id"},"description":"Filter to a single session."},{"name":"user_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter to one SDR's calls.","title":"User Email"},"description":"Filter to one SDR's calls."},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Start date \"YYYY-MM-DD\".","title":"Date From"},"description":"Start date \"YYYY-MM-DD\"."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"End date \"YYYY-MM-DD\".","title":"Date To"},"description":"End date \"YYYY-MM-DD\"."},{"name":"aggregation","in":"query","required":false,"schema":{"type":"string","description":"\"DAILY\" for per-day rows, \"TOTAL\" for one summary row.","default":"DAILY","title":"Aggregation"},"description":"\"DAILY\" for per-day rows, \"TOTAL\" for one summary row."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerStatsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/dialer/numbers":{"get":{"tags":["Voice"],"summary":"List dialer-eligible phone numbers","description":"List phone numbers available to the dialer for this org.\n\nEach row carries seven-day usage stats (``calls_today``, ``calls_7d``,\n``connect_rate_7d``) and the ``daily_limit`` so an agent can choose\nthe next number to use without a follow-up call.","operationId":"list_dialer_numbers_voice_dialer_numbers_get","parameters":[{"name":"user_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Optional - restrict to numbers assigned to a specific SDR.","title":"User Email"},"description":"Optional - restrict to numbers assigned to a specific SDR."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerNumbersListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/dialer/missed-callbacks":{"get":{"tags":["Voice"],"summary":"List missed inbound callbacks","description":"Inbound calls that were not picked up, with caller / contact info.","operationId":"list_missed_callbacks_voice_dialer_missed_callbacks_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Max rows to return.","default":50,"title":"Limit"},"description":"Max rows to return."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MissedCallbacksResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/dialer/calls/{room_name}/grading":{"get":{"tags":["Voice"],"summary":"Get AI call grading for a single dialer call","description":"Return the AI-generated grading payload for a dialer call.\n\nReturns ``status=\"pending\"`` when grading is still being computed\n(voice responds 204). Returns 404 if the call does not exist for the\ncaller's org.","operationId":"get_call_grading_voice_dialer_calls__room_name__grading_get","parameters":[{"name":"room_name","in":"path","required":true,"schema":{"type":"string","description":"LiveKit room / call identifier (`livekit_room_name`).","title":"Room Name"},"description":"LiveKit room / call identifier (`livekit_room_name`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CallGradingResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/dialer/agents":{"get":{"tags":["Voice"],"summary":"List voice agents available for a dialer session","description":"List voice agents that can be assigned to a parallel-dialer session.\n\nThe chat layer uses this to populate the picker before calling\n``POST /voice/dialer/sessions`` - feed the returned ``agent_id`` into\nthe create body.\n\nReturns up to ``_AGENT_LIST_CAP`` rows (no pagination on the public\nsurface; the picker is meant to fit in one chat turn).","operationId":"list_dialer_agents_voice_dialer_agents_get","parameters":[{"name":"role","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by agent role (e.g. \"SDR\", \"AE\", \"Receptionist\", \"CSM\").","title":"Role"},"description":"Filter by agent role (e.g. \"SDR\", \"AE\", \"Receptionist\", \"CSM\")."},{"name":"agent_status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by status (e.g. \"active\"). Defaults to all.","title":"Agent Status"},"description":"Filter by status (e.g. \"active\"). Defaults to all."},{"name":"entity_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"\"agent\" or \"twin\". Defaults to all.","title":"Entity Type"},"description":"\"agent\" or \"twin\". Defaults to all."},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Substring match on agent name.","title":"Search"},"description":"Substring match on agent name."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerAgentsListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/dialer/sessions/{session_id}/status":{"patch":{"tags":["Voice"],"summary":"Pause, resume, or stop a parallel-dialer session","description":"Lifecycle hook for a dialer session.\n\n- ``PAUSED`` pauses an active session.\n- ``COMPLETED`` ends the session (one-way; reopen requires the\n  voice frontend's manual-dial flow).\n\nTo RESUME a paused session use ``POST /voice/dialer/sessions/{id}/resume``\n— the voice service rejects a PATCH to ``ACTIVE`` (the resume flow is a\nfresh start-session call), so ``ACTIVE`` is rejected here with a 422 that\npoints at the correct endpoint rather than forwarding an opaque 400.\n\n``FAILED`` is reserved for system use and is rejected here.","operationId":"update_dialer_session_status_voice_dialer_sessions__session_id__status_patch","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Session UUID.","title":"Session Id"},"description":"Session UUID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DialerSessionStatusUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerSessionStatusUpdateResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/dialer/sessions/{session_id}/resume":{"post":{"tags":["Voice"],"summary":"Resume a paused parallel-dialer session by auto-fetching next batch","description":"Resume a PAUSED parallel-dialer session.\n\nThe voice service's ``PATCH /sessions/{id}/status`` rejects\n``ACTIVE`` - the real resume flow is to call ``start-session`` again\nwith the existing ``session_id`` and a fresh batch of contacts. This\nroute does the lookup + filtering + forwarding in one shot so an MCP\ncaller only has to supply the session id (and optionally a batch\nsize).\n\nSteps performed server-side:\n\n1. Fetch the session via ``GET /api/parallel-calls/sessions``\n   (filtered to the caller's org). Voice has no per-id GET, so we\n   page with ``page_size=200`` and find the row.\n2. Verify the session belongs to the caller's org and is in the\n   ``PAUSED`` state. ACTIVE / COMPLETED sessions return 422.\n3. Read ``list_id`` and the ``list_offset`` cursor from\n   ``session_metadata``. Sessions created without a ``list_id``\n   (ad-hoc / campaign-mode) cannot be resumed via this route and\n   return 422.\n4. Page contacts out of the source list starting at the cursor,\n   skipping rows already in ``session.contact_ids`` and rows that\n   have no usable phone field.\n5. Forward up to ``max_contacts`` rows to voice's\n   ``/api/parallel-calls/start-session`` with the existing\n   ``session_id``. Voice de-duplicates active calls within the\n   session and auto-promotes status to ACTIVE on success.\n\nThe ``list_offset`` we send back to voice is advanced by the total\nnumber of rows we read from the list (called + skipped + dialed) so\na future resume picks up where we left off, not where the previous\npause cursor sat.","operationId":"resume_dialer_session_voice_dialer_sessions__session_id__resume_post","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Session UUID.","title":"Session Id"},"description":"Session UUID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DialerSessionResumeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerSessionResumeResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/dialer/calls/{room_name}/transcript":{"get":{"tags":["Voice"],"summary":"Get the persisted transcript for a single dialer call","description":"Return the speaker-segmented transcript for a dialer call.\n\n``status=\"empty\"`` indicates the call row exists but the transcript\nhas not yet been flushed to the database (the call may still be in\nprogress, or the persistor may be in-flight). 404 is raised if the\ncall does not exist for the caller's org.\n\nThe voice service is org-scoped server-side: we forward the caller's\norg id so any cross-tenant row is treated as not-found.","operationId":"get_call_transcript_voice_dialer_calls__room_name__transcript_get","parameters":[{"name":"room_name","in":"path","required":true,"schema":{"type":"string","description":"LiveKit room / call identifier (`livekit_room_name`).","title":"Room Name"},"description":"LiveKit room / call identifier (`livekit_room_name`)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CallTranscriptResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/dialer/calls":{"get":{"tags":["Voice"],"summary":"List dialer calls (filter by contact, SDR, or session)","description":"Return up to ``limit`` recent dialer call summaries.\n\nAt least ONE of (contact_id, user_email, parallel_session_id) MUST\nbe supplied - org id alone is not a valid filter (would firehose\nthe entire org's call history). 422 otherwise.\n\nSummary rows do NOT include the transcript blob (5-50 KB each).\nUse ``has_transcript`` to decide whether to fetch the full\ntranscript via ``GET /voice/dialer/calls/{room_name}/transcript``.\n\nOrg isolation is enforced server-side by the voice route: the org id\non the API key is forwarded as a required query param, so a call row\nfrom another tenant cannot leak into the response.","operationId":"list_calls_for_contact_voice_dialer_calls_get","parameters":[{"name":"contact_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"CDP contact id (string form of mashup_contacts.id). If you only have a CRM-overlay id (cb_contact_extensions.id), resolve it via the contacts endpoint first. Optional - supply at least one of contact_id, user_email, or parallel_session_id.","title":"Contact Id"},"description":"CDP contact id (string form of mashup_contacts.id). If you only have a CRM-overlay id (cb_contact_extensions.id), resolve it via the contacts endpoint first. Optional - supply at least one of contact_id, user_email, or parallel_session_id."},{"name":"user_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"SDR email. Returns dialer calls where the parent ParallelDialSession.user_email matches. Use for incremental ingestion of one SDR's call history.","title":"User Email"},"description":"SDR email. Returns dialer calls where the parent ParallelDialSession.user_email matches. Use for incremental ingestion of one SDR's call history."},{"name":"parallel_session_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter to a single ParallelDialSession.session_id.","title":"Parallel Session Id"},"description":"Filter to a single ParallelDialSession.session_id."},{"name":"created_after","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO-8601 timestamp. Only return calls with created_at >= this value. Use for incremental polling (pass the max created_at from the previous page on the next call).","title":"Created After"},"description":"ISO-8601 timestamp. Only return calls with created_at >= this value. Use for incremental polling (pass the max created_at from the previous page on the next call)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Max calls to return, newest first. Capped at 100.","default":20,"title":"Limit"},"description":"Max calls to return, newest first. Capped at 100."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CallsListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/agents":{"post":{"tags":["Voice"],"summary":"Create a voice agent or twin","description":"Create a new voice agent or twin bound to the caller's org.\n\nOrg is pinned server-side from the API key. The agent's creator is set\nserver-side too, never from the request body: an agent is credited to the\nperson who created the API key. A twin, or an agent created with a key\nthat records no creator, is credited to the key itself.","operationId":"create_voice_agent_voice_agents_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VoiceAgentCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceAgentResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"get":{"tags":["Voice"],"summary":"List voice agents and twins","description":"List agents and twins for the caller's org, with filtering + paging.\n\nThis is the full management list (persona/identity summary fields\nincluded). ``GET /voice/dialer/agents`` above stays as the lighter\npicker shape used by the dialer/chat flows - unchanged.","operationId":"list_voice_agents_voice_agents_get","parameters":[{"name":"entity_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by entity type (\"agent\" or \"twin\").","title":"Entity Type"},"description":"Filter by entity type (\"agent\" or \"twin\")."},{"name":"role","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by agent role.","title":"Role"},"description":"Filter by agent role."},{"name":"agent_status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by status.","title":"Agent Status"},"description":"Filter by status."},{"name":"is_template","in":"query","required":false,"schema":{"anyOf":[{"type":"boolean"},{"type":"null"}],"description":"true=templates only, false=non-templates only.","title":"Is Template"},"description":"true=templates only, false=non-templates only."},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Substring match on agent name.","title":"Search"},"description":"Substring match on agent name."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (1-indexed).","default":1,"title":"Page"},"description":"Page number (1-indexed)."},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Results per page (max 100).","default":20,"title":"Page Size"},"description":"Results per page (max 100)."},{"name":"sort_by","in":"query","required":false,"schema":{"type":"string","description":"\"created_at\" | \"agent_name\" | \"role\" | \"status\".","default":"created_at","title":"Sort By"},"description":"\"created_at\" | \"agent_name\" | \"role\" | \"status\"."},{"name":"sort_order","in":"query","required":false,"schema":{"type":"string","description":"\"asc\" or \"desc\".","default":"desc","title":"Sort Order"},"description":"\"asc\" or \"desc\"."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceAgentListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/agents/{agent_id}":{"get":{"tags":["Voice"],"summary":"Get a voice agent or twin by id","description":"Fetch one agent's full configuration.\n\norg_id is forwarded as a query param pinned to the caller - voice\nfilters `AgentSettings` by `(org_id, agent_id)`, so another org's\nagent id 404s here exactly like a nonexistent one.","operationId":"get_voice_agent_voice_agents__agent_id__get","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","description":"Agent UUID.","title":"Agent Id"},"description":"Agent UUID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceAgentResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"put":{"tags":["Voice"],"summary":"Update a voice agent or twin","description":"Partially update an agent. Only fields present in the body change.\n\n``persona`` / ``identity`` / ``knowledge`` are component-level\nreplacements, not deep merges - matching voice's own update semantics\n(send the field's full sub-object to change any part of it). org_id\nis pinned server-side; a cross-org agent_id 404s the same as GET.","operationId":"update_voice_agent_voice_agents__agent_id__put","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","description":"Agent UUID.","title":"Agent Id"},"description":"Agent UUID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VoiceAgentUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceAgentResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Voice"],"summary":"Delete a voice agent or twin","description":"Cascade-delete an agent or twin: its persona, identity, knowledge\nand parent settings row all go with it (voice's own cascade, not\nsomething this proxy orchestrates). Requires the ``voice:write``\nscope explicitly - see ``require_voice_agent_delete`` above for why\nthis is self-gated rather than driving a new ``voice:delete`` scope.\n\norg_id is pinned server-side; voice filters by ``(org_id, agent_id)``\nso a cross-org agent_id 404s the same as GET/PUT.","operationId":"delete_voice_agent_voice_agents__agent_id__delete","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","description":"Agent UUID.","title":"Agent Id"},"description":"Agent UUID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceAgentResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/calls":{"post":{"tags":["Voice"],"summary":"Dispatch one ad-hoc AI-agent call to a raw number","description":"Dispatch a single AI-agent call to an arbitrary number right now.\n\nNo dialer session or contact list required - this wraps voice's\n``POST /api/call/start`` (`voice/graph8_livekit/routers/call.py:19`),\nthe one-off \"call this number\" primitive that previously had no public\nsurface at all. Places a REAL call and is billable upstream (voice\nchecks the org's subscription and concurrent-call cap before\ndispatching). Send an ``Idempotency-Key`` header to make a retry\nsafe - every POST on this API already honors it via the app-wide\n``IdempotencyMiddleware``, so no extra field is needed here.\n\nOrg is pinned server-side; phone numbers are normalized to E.164 by\nvoice itself (a malformed number 400s with an actionable message).","operationId":"start_voice_call_voice_calls_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VoiceCallStartRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceCallStartResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/dispositions":{"get":{"tags":["Voice"],"summary":"List system + org custom call dispositions","description":"System dispositions (with connected classification) plus this org's\ncustom ones, and how many of the ``custom_limit`` are used.","operationId":"list_voice_dispositions_voice_dispositions_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceDispositionListResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"post":{"tags":["Voice"],"summary":"Create a custom call disposition","description":"Create an org-level custom disposition (max 10 per org).\n\nVoice enforces the cap, the preset color palette, and case-insensitive\nname uniqueness against both system and existing custom dispositions -\nerrors surface as 400/409 with voice's own detail message.","operationId":"create_voice_disposition_voice_dispositions_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VoiceCustomDispositionCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceCustomDispositionItem_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/dispositions/{disposition_id}":{"patch":{"tags":["Voice"],"summary":"Edit a custom call disposition","description":"Edit a custom disposition. Only supplied fields change.\n\n``is_connected`` is locked by voice once any call already references\nthe disposition (would retroactively re-classify historical calls) -\nthat 409 is forwarded as-is. A disposition belonging to another org\n404s (voice's ``_load_disposition_for_org`` checks the stored row's\norg against ``X-Org-Id`` before allowing the edit).","operationId":"update_voice_disposition_voice_dispositions__disposition_id__patch","parameters":[{"name":"disposition_id","in":"path","required":true,"schema":{"type":"integer","description":"Custom disposition id.","title":"Disposition Id"},"description":"Custom disposition id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VoiceCustomDispositionUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoiceCustomDispositionItem_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/dialer/sessions/draft":{"post":{"tags":["Dialer"],"summary":"Create Session Draft","description":"CONTACTS NOBODY. Creates a DRAFT session and dials no one.\n\nThe safe first step: it resolves the list or sequence, snapshots the\nfilter, and stops. `POST /dialer/sessions/{id}/next-batch` is what turns a\ndraft into ringing telephones.\n\nNot idempotent in the way it looks: voice REUSES a live session for the\nsame list rather than creating a second one, so calling this twice does\nnot double-dial - it returns the existing session. `from_phone` is\noptional here and enforced at dial time.","operationId":"create_session_draft_dialer_sessions_draft_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SessionDraftRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/sessions/{session_id}/next-batch":{"post":{"tags":["Dialer"],"summary":"Dial Next Batch","description":"*** CALLS REAL PEOPLE. *** This is the operation that dials.\n\nVoice's own words for this handler are \"the one-and-only dial path for\nBE-owned queue sessions\" (`dialer_sessions.py:2272`). It picks the next\ncontacts off the queue and places outbound calls to them, transitioning\nthe session DRAFT -> ACTIVE or PAUSED -> ACTIVE on the way.\n\n`parallel_count` is HOW MANY PEOPLE ARE CALLED AT ONCE. Sending it with a\nsession configured for one is how a power-dial becomes a parallel dial.\n\nEach attempt reserves credits and each connected minute charges more, so\nthis both spends money and reaches strangers. It is tiered `external`\nrather than `write` for exactly that reason: \"dial the next twenty people\"\nmust not be grantable by the same scope as \"rename a session\".\n\n`filter_spec` sent here CHANGES WHO IS ELIGIBLE before the batch is\npicked. It is not a display filter.","operationId":"dial_next_batch_dialer_sessions__session_id__next_batch_post","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session to dial.","title":"Session Id"},"description":"Session to dial."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NextBatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/dialer/sessions/calls/hangup":{"post":{"tags":["Dialer"],"summary":"Hangup Session Call","description":"CONTACTS NOBODY NEW. Ends a call that is already up.\n\nThis is the STOP button, not a dial. It gates on `voice:dialer:control`\nrather than the create permission on purpose: hanging up is the action you\nwant an operator to be able to take without also being able to start a\nsession.\n\nThe completion record is written by Twilio's status webhook afterwards, so\nthe disposition and duration appear a moment later, not in this response.","operationId":"hangup_session_call_dialer_sessions_calls_hangup_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CallControlRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/sessions/calls/drop-voicemail":{"post":{"tags":["Dialer"],"summary":"Drop Session Voicemail","description":"*** REACHES A REAL PERSON. *** Leaves a voicemail on their phone.\n\nThe recording is played in the rep's CLONED VOICE and the call is then\nhung up with disposition `voicemail`. The person hears it; there is no\nundo, and a wrong `call_id` leaves the message on the wrong stranger's\nphone.\n\nTiered `external`, not `write`: it reaches a human outside graph8.","operationId":"drop_session_voicemail_dialer_sessions_calls_drop_voicemail_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VoicemailDropRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/dialer/sessions/{session_id}/calls/skip-contact":{"post":{"tags":["Dialer"],"summary":"Skip Contact","description":"CONTACTS NOBODY. Marks a contact so the queue stops offering them.\n\nQueue bookkeeping. Reversible with `unskip-contact`, which is why this is\nan ordinary `write` and not a destructive tier.","operationId":"skip_contact_dialer_sessions__session_id__calls_skip_contact_post","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id.","title":"Session Id"},"description":"Session id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SkipContactRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/sessions/{session_id}/calls/unskip-contact":{"post":{"tags":["Dialer"],"summary":"Unskip Contact","description":"CONTACTS NOBODY. Puts a skipped contact back in the queue.\n\nIt does NOT call them - it only makes them eligible again, so the next\n`next-batch` may.","operationId":"unskip_contact_dialer_sessions__session_id__calls_unskip_contact_post","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id.","title":"Session Id"},"description":"Session id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SkipContactRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/sessions/prewarm-voicemails":{"post":{"tags":["Dialer"],"summary":"Prewarm Voicemails","description":"CONTACTS NOBODY - but it SPENDS. Synthesises voicemail audio in advance.\n\nText-to-speech is generated per contact and cached so the audio is ready\nbefore a rep clicks Start Dialing. No phone rings and no one hears\nanything, but it is real generation work per contact, which is why it is\ntiered `billable` rather than a plain `write`.\n\nReturns immediately - the work is fired in the background. Duplicates are\nno-ops (Redis in-flight lock plus a per-contact cache). Voice caps the\nbatch at 20 and so does this contract.","operationId":"prewarm_voicemails_dialer_sessions_prewarm_voicemails_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PrewarmVoicemailsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/dialer/sessions/calls/mute":{"post":{"tags":["Dialer"],"summary":"Mute Call","description":"CONTACTS NOBODY NEW. Mutes the rep on a call already in progress.\n\n`muted` is explicit rather than a toggle, so a retried request is\nidempotent instead of un-muting someone mid-sentence.","operationId":"mute_call_dialer_sessions_calls_mute_post","parameters":[{"name":"call_id","in":"query","required":true,"schema":{"type":"string","description":"The live call to mute.","title":"Call Id"},"description":"The live call to mute."},{"name":"muted","in":"query","required":false,"schema":{"type":"boolean","description":"`true` mutes the rep, `false` unmutes.","default":true,"title":"Muted"},"description":"`true` mutes the rep, `false` unmutes."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/sessions/token":{"get":{"tags":["Dialer"],"summary":"Mint Softphone Token","description":"CONTACTS NOBODY - but the RESPONSE CAN. Mints a softphone credential.\n\nReturns a short-lived (1 hour) Twilio access token carrying a VoiceGrant,\nfor a browser running the Twilio Voice SDK. Whoever holds it can register a\ndevice and place and receive calls as `sdr_{user_id}_{org}` until it\nexpires. TREAT THE RESPONSE AS A SECRET: it is a bearer credential, not a\ndescription of one.\n\nThat is why this is the one GET on this router tiered `external` instead of\n`read`, and why it gates on `voice:calls:place` rather than a read\npermission - a read-only key must not be able to mint the ability to dial.\n\n`user_id` is REQUIRED here although voice defaults it. An organisation API\nkey has no user of its own, and defaulting would mint a credential for an\nidentity nobody named. The organisation half of the identity is always the\nkey's own and cannot be supplied.","operationId":"mint_softphone_token_dialer_sessions_token_get","parameters":[{"name":"user_id","in":"query","required":true,"schema":{"type":"string","description":"The rep this softphone credential is for.","title":"User Id"},"description":"The rep this softphone credential is for."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/dialer/sessions/{session_id}/ws-ticket":{"post":{"tags":["Dialer"],"summary":"Mint Session Ws Ticket","description":"CONTACTS NOBODY. Mints a one-shot ticket for the session event stream.\n\nThe WebSocket itself is not part of this contract - a socket cannot be\ndescribed as a request/response operation or generated into an SDK method.\nThis mints the ticket that opens one, which IS an ordinary POST.","operationId":"mint_session_ws_ticket_dialer_sessions__session_id__ws_ticket_post","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session to subscribe to.","title":"Session Id"},"description":"Session to subscribe to."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/sessions/calls/{call_id}/ws-ticket":{"post":{"tags":["Dialer"],"summary":"Mint Transcript Ws Ticket","description":"CONTACTS NOBODY. Mints a one-shot ticket for the live transcript stream.\n\nSame shape as the session ticket, different stream: this one carries the\nwords of a call as it happens.","operationId":"mint_transcript_ws_ticket_dialer_sessions_calls__call_id__ws_ticket_post","parameters":[{"name":"call_id","in":"path","required":true,"schema":{"type":"string","description":"Call to stream the transcript of.","title":"Call Id"},"description":"Call to stream the transcript of."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/sessions/{session_id}/grid":{"post":{"tags":["Dialer"],"summary":"Read Session Grid","description":"CONTACTS NOBODY. Reads a page of the session's contact grid.\n\nA POST because the filter and sort specification is too large for a query\nstring, not because it changes anything - it mutates nothing and dials\nnobody. Tiered `read` by an explicit rule for that reason, so a read-only\nkey can page through a queue.","operationId":"read_session_grid_dialer_sessions__session_id__grid_post","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id.","title":"Session Id"},"description":"Session id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/GridPageRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/dialer/sessions/{session_id}/filter-spec":{"patch":{"tags":["Dialer"],"summary":"Update Session Filter","description":"CONTACTS NOBODY DIRECTLY - but it decides WHO IS CALLED NEXT.\n\nThe filter is the queue's eligibility rule, not a view. Widening it on a\nrunning session adds people who will then be dialed by the next\n`next-batch`; narrowing it removes people mid-campaign. No call is placed\nby this request itself.","operationId":"update_session_filter_dialer_sessions__session_id__filter_spec_patch","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id.","title":"Session Id"},"description":"Session id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FilterSpecPatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/sessions/{session_id}/booking-event-type":{"patch":{"tags":["Dialer"],"summary":"Update Session Booking Event Type","description":"CONTACTS NOBODY. Sets which meeting type a booking on this session creates.\n\nNull clears the selection and falls back to the org default.","operationId":"update_session_booking_event_type_dialer_sessions__session_id__booking_event_type_patch","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id.","title":"Session Id"},"description":"Session id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BookingEventTypePatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/sessions/{session_id}/hidden-custom-fields":{"patch":{"tags":["Dialer"],"summary":"Update Session Hidden Fields","description":"CONTACTS NOBODY. Hides columns in the rep's grid. Display only.\n\nPUT semantics: the list REPLACES whatever was hidden before, so send the\nwhole set rather than the delta. Hiding a field does not remove the data.","operationId":"update_session_hidden_fields_dialer_sessions__session_id__hidden_custom_fields_patch","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id.","title":"Session Id"},"description":"Session id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/HiddenCustomFieldsPatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/sessions/{session_id}/queue-stats":{"get":{"tags":["Dialer"],"summary":"Read Queue Stats","description":"CONTACTS NOBODY. How much of the queue is left, and what has been worked.","operationId":"read_queue_stats_dialer_sessions__session_id__queue_stats_get","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id.","title":"Session Id"},"description":"Session id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/dialer/sessions/assurance/provider-receipt":{"get":{"tags":["Dialer"],"summary":"Read Provider Receipt","description":"CONTACTS NOBODY. The telephony provider's assurance receipt for this org.\n\nDeclared BEFORE `/sessions/{session_id}/queue-stats` would be a concern if\nthe two overlapped; they do not - `assurance/provider-receipt` and\n`{session_id}/queue-stats` differ in their second segment, so neither can\nswallow the other. The org is the key's own and is not a parameter.","operationId":"read_provider_receipt_dialer_sessions_assurance_provider_receipt_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/sessions":{"post":{"tags":["Dialer"],"summary":"Create Paused Parallel Session","description":"CONTACTS NOBODY. Creates a PAUSED parallel session.\n\nThe session exists and is configured, and not one telephone rings. This is\nthe safe half of the pair - `POST /dialer/parallel-calls/sessions/start`\nis the half that dials.\n\nPublished as a POST to the collection precisely because that is what a\ncustomer will reach for first, and the harmless operation should be the\none they land on by guessing.","operationId":"create_paused_parallel_session_dialer_parallel_calls_sessions_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreatePausedSessionRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/sessions/start":{"post":{"tags":["Dialer"],"summary":"Start Parallel Session","description":"*** CALLS REAL PEOPLE. *** Dials every contact in the body, at once.\n\nOne request can ring a lot of telephones. The only ceiling is voice's\nper-org `MAX_LIMIT_OF_CALLS_PER_ORG_ID`; this contract does not cap\n`contacts` itself, because a cap here that disagreed with voice's would\nreject batches voice would have accepted.\n\nContacts whose number cannot be parsed are SKIPPED, not rejected - the\nbatch proceeds without them and the response names who was dropped. Read\nit; do not assume every contact you sent was dialed.\n\nAttempts reserve credits and connected minutes charge more. Tiered\n`external`: this reaches strangers on the customer's behalf.","operationId":"start_parallel_session_dialer_parallel_calls_sessions_start_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StartParallelSessionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/manual-dial":{"post":{"tags":["Dialer"],"summary":"Manual Dial","description":"*** CALLS A REAL PERSON. *** Dials `to_phone` immediately.\n\nAn arbitrary number, inside an existing PAUSED or COMPLETED session. If\nthe session is ACTIVE voice refuses rather than dialing over a running\ncampaign.\n\nThe number does not have to belong to a contact: an unknown number is\nresolved to an existing contact by phone, or a new contact is created for\nit, so the call is attributable afterwards. That means this operation can\nCREATE A CONTACT RECORD as a side effect.\n\nSelf-dialing is refused. Tiered `external`.","operationId":"manual_dial_dialer_parallel_calls_manual_dial_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ManualDialRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/redial-contact":{"post":{"tags":["Dialer"],"summary":"Redial Contact","description":"*** CALLS A REAL PERSON AGAIN. *** Redials a contact already tried.\n\nVoice caps attempts per contact (`MAX_REDIAL_ATTEMPTS`) and refuses past\nit, which is the guard against a retry loop becoming harassment - so treat\na 400 here as \"stop\", not as \"retry\".\n\nIt runs the same credit preflight the first dial does and can fail with\n`insufficient_credits`, reserving the attempt fee plus connected minutes.\nTiered `external`.","operationId":"redial_contact_dialer_parallel_calls_redial_contact_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RedialContactRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/calls/hangup":{"post":{"tags":["Dialer"],"summary":"Hangup Parallel Call","description":"CONTACTS NOBODY NEW. Ends one leg of a parallel session.\n\nThe other legs keep ringing. Gated on `voice:dialer:control`, the same\npermission voice declares - re-declared here because voice's own gate does\nnot run for a server-to-server call.","operationId":"hangup_parallel_call_dialer_parallel_calls_calls_hangup_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/HangupCallRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/calls/{livekit_room_name}/drop-voicemail":{"post":{"tags":["Dialer"],"summary":"Drop Parallel Voicemail","description":"*** REACHES A REAL PERSON. *** Leaves a voicemail and hangs up.\n\nThe script is played in the rep's cloned voice and the call is closed with\ndisposition `voicemail`. The person hears it. There is no undo.\n\nThe command is queued for the agent on the call (a 120-second window), so\na 200 means \"accepted\", not \"already played\". Tiered `external`.","operationId":"drop_parallel_voicemail_dialer_parallel_calls_calls__livekit_room_name__drop_voicemail_post","parameters":[{"name":"livekit_room_name","in":"path","required":true,"schema":{"type":"string","description":"Room name of the live call.","title":"Livekit Room Name"},"description":"Room name of the live call."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/calls/{livekit_room_name}/disposition":{"patch":{"tags":["Dialer"],"summary":"Set Call Disposition","description":"CONTACTS NOBODY. Records how a finished call went.\n\n`disposition` is an open string rather than a closed enum because the\nvocabulary is the system set PLUS the org's own custom dispositions -\nclosing it here would refuse a value the customer defined.\n`GET /voice/dispositions` lists what this organisation accepts.\n\nSetting `callback_at` schedules the follow-up; it does not place it.","operationId":"set_call_disposition_dialer_parallel_calls_calls__livekit_room_name__disposition_patch","parameters":[{"name":"livekit_room_name","in":"path","required":true,"schema":{"type":"string","description":"Room name of the call.","title":"Livekit Room Name"},"description":"Room name of the call."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CallDispositionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/sessions/{session_id}/contact-ids-by-disposition":{"get":{"tags":["Dialer"],"summary":"List Contact Ids By Disposition","description":"CONTACTS NOBODY. Which contacts in a session ended at a given outcome.\n\n`latest` and `has_ever` differ for a redialed contact: a `no_answer` that\nlater connected is in `has_ever` but not in `latest`. An unrecognised mode\nfalls back to `latest` rather than erroring, matching voice.","operationId":"list_contact_ids_by_disposition_dialer_parallel_calls_sessions__session_id__contact_ids_by_disposition_get","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id.","title":"Session Id"},"description":"Session id."},{"name":"disposition","in":"query","required":true,"schema":{"type":"string","description":"Disposition, or several comma-separated.","title":"Disposition"},"description":"Disposition, or several comma-separated."},{"name":"mode","in":"query","required":false,"schema":{"type":"string","description":"`latest` = current outcome; `has_ever` = any attempt.","default":"latest","title":"Mode"},"description":"`latest` = current outcome; `has_ever` = any attempt."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/sessions/{session_id}/redial-state":{"patch":{"tags":["Dialer"],"summary":"Update Redial State","description":"CONTACTS NOBODY. Records how far a bulk redial sweep has got.\n\nBookkeeping so a sweep can resume where it stopped. `reset: true` clears\nit, which makes the NEXT sweep start from the beginning - it does not\nitself redial anyone.","operationId":"update_redial_state_dialer_parallel_calls_sessions__session_id__redial_state_patch","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id.","title":"Session Id"},"description":"Session id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateRedialStateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/analytics/dialer-report":{"get":{"tags":["Dialer"],"summary":"Read Dialer Report","description":"CONTACTS NOBODY. Dial counts, connect rates and outcomes.\n\n`aggregation` is closed to the app's own two values, so a typo is a 422\nnaming them rather than a silent fallback to daily.\n\n`client_tz` decides where a day starts. Omitting it on a distributed team\nis the usual reason two people get different numbers for \"yesterday\".","operationId":"read_dialer_report_dialer_parallel_calls_analytics_dialer_report_get","parameters":[{"name":"session_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Restrict to one session.","title":"Session Id"},"description":"Restrict to one session."},{"name":"user_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Restrict to one rep.","title":"User Email"},"description":"Restrict to one rep."},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO date, inclusive.","title":"Date From"},"description":"ISO date, inclusive."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO date, inclusive.","title":"Date To"},"description":"ISO date, inclusive."},{"name":"aggregation","in":"query","required":false,"schema":{"enum":["daily","total"],"type":"string","description":"`daily` buckets; `total` collapses.","default":"daily","title":"Aggregation"},"description":"`daily` buckets; `total` collapses."},{"name":"client_tz","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"IANA zone the day boundaries are cut on.","title":"Client Tz"},"description":"IANA zone the day boundaries are cut on."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/missed-callbacks/seen":{"patch":{"tags":["Dialer"],"summary":"Mark Missed Callbacks Seen","description":"CONTACTS NOBODY. Marks specific missed callbacks as seen.\n\nSeen is not resolved: it clears the notification, it does not say anyone\ncalled back. `resolve` is the separate, meaningful one.","operationId":"mark_missed_callbacks_seen_dialer_parallel_calls_missed_callbacks_seen_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MissedCallbacksSeenRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/missed-callbacks/seen-all":{"patch":{"tags":["Dialer"],"summary":"Mark All Missed Callbacks Seen","description":"CONTACTS NOBODY. Clears the whole missed-callback badge for one rep.\n\nThe app carries the organisation in the PATH here\n(`/missed-callbacks/seen-all/{org_id}`). That segment is NOT published: a\ncaller must never be able to name the tenant it is clearing, so the org\ncomes from the key and the path ends at `seen-all`.","operationId":"mark_all_missed_callbacks_seen_dialer_parallel_calls_missed_callbacks_seen_all_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MissedCallbacksSeenAllRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/missed-callbacks/resolve":{"patch":{"tags":["Dialer"],"summary":"Resolve Missed Callbacks","description":"CONTACTS NOBODY. Closes a missed callback.\n\n`resolution` is closed to `manual` (someone called them back) or `ignored`\n(a decision not to). The two are not interchangeable in reporting, which\nis why the field exists at all rather than a single \"done\" flag.","operationId":"resolve_missed_callbacks_dialer_parallel_calls_missed_callbacks_resolve_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MissedCallbacksResolveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/missed-callbacks/unresolve":{"patch":{"tags":["Dialer"],"summary":"Unresolve Missed Callbacks","description":"CONTACTS NOBODY. Reopens a missed callback closed by mistake.","operationId":"unresolve_missed_callbacks_dialer_parallel_calls_missed_callbacks_unresolve_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MissedCallbacksUnresolveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/recordings/ownership":{"get":{"tags":["Dialer"],"summary":"Check Recording Ownership","description":"CONTACTS NOBODY. Does THIS organisation own the recording at `url`?\n\nAnswered from the call rows rather than the storage prefix, because\nrecordings moved between organisations by the merge migration keep the\nSOURCE org's prefix while belonging to the target. Fail-closed: anything\nthat goes wrong answers \"not owned\".\n\nThe organisation asked about is always the key's own - it is not a\nparameter, so this cannot be used to probe another tenant's storage.","operationId":"check_recording_ownership_dialer_parallel_calls_recordings_ownership_get","parameters":[{"name":"url","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":2048,"description":"Stored recording URL.","title":"Url"},"description":"Stored recording URL."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/targets":{"get":{"tags":["Dialer"],"summary":"Read Org Targets","description":"CONTACTS NOBODY. The organisation's daily dial and meeting goals.","operationId":"read_org_targets_dialer_parallel_calls_targets_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"put":{"tags":["Dialer"],"summary":"Set Org Targets","description":"CONTACTS NOBODY. Sets the organisation's daily goals. Upserts.\n\nVoice takes these as QUERY parameters and applies its defaults (250 dials,\n3 meetings) to anything omitted, so a partial update SILENTLY RESETS the\nfield you left out. That behaviour is preserved rather than papered over -\nbut it is a body here, and the defaults are stated, so the reset is at\nleast visible in the contract. Send both fields every time.","operationId":"set_org_targets_dialer_parallel_calls_targets_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OrgDialerTargetsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/targets/all-sdrs":{"get":{"tags":["Dialer"],"summary":"Read All Sdr Targets","description":"CONTACTS NOBODY. Per-rep goals for everyone in the organisation.\n\nA two-segment LITERAL under `/targets`. Nothing registers\n`/parallel-calls/targets/{something}`, so it cannot be swallowed - and the\nshadowing test asserts that rather than trusting it.","operationId":"read_all_sdr_targets_dialer_parallel_calls_targets_all_sdrs_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/targets/sdr":{"put":{"tags":["Dialer"],"summary":"Set Sdr Targets","description":"CONTACTS NOBODY. Overrides one rep's daily goals.\n\nBoth targets are REQUIRED here although voice would accept either -\nthe org-level route's silent-reset behaviour is the reason, and requiring\nboth makes a partial write impossible rather than merely documented.","operationId":"set_sdr_targets_dialer_parallel_calls_targets_sdr_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SdrDialerTargetsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Dialer"],"summary":"Clear Sdr Targets","description":"CONTACTS NOBODY. Removes one rep's override; they fall back to the org goal.\n\nSelf-gated on the EXISTING `voice:write` scope rather than minting a\n`voice:delete` for two routes - `action_for()` maps DELETE to a `delete`\naction unconditionally otherwise, and a new scope strands every key minted\nbefore it. Same choice `DELETE /voice/agents/{agent_id}` already made.","operationId":"clear_sdr_targets_dialer_parallel_calls_targets_sdr_delete","parameters":[{"name":"sdr_email","in":"query","required":true,"schema":{"type":"string","description":"The rep whose override is removed.","title":"Sdr Email"},"description":"The rep whose override is removed."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/calls/{livekit_room_name}/grading/review":{"post":{"tags":["Dialer"],"summary":"Mark Grading Reviewed","description":"CONTACTS NOBODY. Marks a call's AI grading as reviewed by a human.\n\nAn acknowledgement, not a re-grade: it changes no score and runs no model.","operationId":"mark_grading_reviewed_dialer_parallel_calls_calls__livekit_room_name__grading_review_post","parameters":[{"name":"livekit_room_name","in":"path","required":true,"schema":{"type":"string","description":"Room name of the graded call.","title":"Livekit Room Name"},"description":"Room name of the graded call."},{"name":"sdr_email","in":"query","required":true,"schema":{"type":"string","description":"The rep whose grading was reviewed.","title":"Sdr Email"},"description":"The rep whose grading was reviewed."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/grading/backfill":{"post":{"tags":["Dialer"],"summary":"Backfill Grading","description":"CONTACTS NOBODY - but it SPENDS, and it can spend a lot.\n\nWith `dry_run=false` this runs AI grading over EVERY ungraded call with a\ntranscript in the window - a model invocation each, one call every two\nseconds, with no ceiling other than how many calls exist. On a busy\norganisation over 365 days that is an unbounded bill from one request.\n\n`dry_run` defaults to TRUE and genuinely short-circuits before any grading\n(`parallel_calls.py:4602`), returning the eligible count and a sample.\nCall it that way first and read the count.\n\nTiered `billable`, not `write`: it reaches a paid model per record.","operationId":"backfill_grading_dialer_parallel_calls_grading_backfill_post","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"How far back to look.","default":30,"title":"Days"},"description":"How far back to look."},{"name":"dry_run","in":"query","required":false,"schema":{"type":"boolean","description":"`true` counts and samples; `false` GRADES AND SPENDS.","default":true,"title":"Dry Run"},"description":"`true` counts and samples; `false` GRADES AND SPENDS."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/grading/campaign-readiness":{"get":{"tags":["Dialer"],"summary":"Check Campaign Readiness","description":"CONTACTS NOBODY. Whether this org has enough graded calls to report on.\n\nA precondition check for the grading dashboards. Reads only.","operationId":"check_campaign_readiness_dialer_parallel_calls_grading_campaign_readiness_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/dialer/transfer/departments":{"get":{"tags":["Dialer"],"summary":"List Transfer Departments","description":"CONTACTS NOBODY. Which departments can take a warm transfer right now.\n\nA LITERAL two-segment path beside `/transfer/{call_id}`, so it is declared\nBEFORE it - registered the other way round, `departments` would be read as\na call id and this route would be unreachable. There is a test that\n`GET /dialer/transfer/<id>` still resolves to the parameter route.","operationId":"list_transfer_departments_dialer_transfer_departments_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/dialer/transfer/{call_id}":{"get":{"tags":["Dialer"],"summary":"Read Transfer Status","description":"CONTACTS NOBODY. Where a warm transfer has got to - ringing, taken, declined.","operationId":"read_transfer_status_dialer_transfer__call_id__get","parameters":[{"name":"call_id","in":"path","required":true,"schema":{"type":"string","description":"Call being transferred.","title":"Call Id"},"description":"Call being transferred."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/dialer/transfer/{call_id}/decline":{"post":{"tags":["Dialer"],"summary":"Decline Transfer","description":"AFFECTS A LIVE CALL WITH A PERSON ON IT, but places no new call.\n\nThe colleague passes on the transfer. The CALLER - a real human - STAYS ON\nHOLD until the ring times out; declining does not hang up on them and does\nnot tell them anything. Worth knowing before wiring this to an\nauto-decline rule.","operationId":"decline_transfer_dialer_transfer__call_id__decline_post","parameters":[{"name":"call_id","in":"path","required":true,"schema":{"type":"string","description":"Call being transferred.","title":"Call Id"},"description":"Call being transferred."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/settings/preferences/{user_email}":{"get":{"tags":["Dialer"],"summary":"Read Dialer Preferences","description":"CONTACTS NOBODY. One rep's dialer preferences.\n\nThe app's path is `/preferences/{org_id}/{user_email}` and its handler\nreads whichever organisation the path names. The org segment is NOT\npublished - it comes from the key - so this cannot read another tenant's\nconfiguration.\n\nVoice additionally refuses to read a rep other than the authenticated one\n(`dialer_settings.py:23-41`). An organisation API key is not a rep, so it\nsupplies the rep the caller named: the tenant boundary holds, the\nrep-versus-rep boundary does not apply to an org credential.","operationId":"read_dialer_preferences_dialer_settings_preferences__user_email__get","parameters":[{"name":"user_email","in":"path","required":true,"schema":{"type":"string","description":"The rep whose preferences to read.","title":"User Email"},"description":"The rep whose preferences to read."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/dialer/settings/preferences":{"put":{"tags":["Dialer"],"summary":"Set Dialer Preferences","description":"CONTACTS NOBODY DIRECTLY - but `call_dnc_contacts` decides WHO MAY BE CALLED.\n\nSetting it true lets the dialer call numbers on a do-not-call list. That is\na COMPLIANCE decision, not a convenience toggle, and it applies to every\nsubsequent dial for this rep.\n\nPATCH semantics despite the verb: only fields you send are changed, and\nomitted ones keep their stored value. The verb is the app's.","operationId":"set_dialer_preferences_dialer_settings_preferences_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DialerPreferencesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/dispositions/{disposition_id}":{"delete":{"tags":["Dialer"],"summary":"Delete Custom Disposition","description":"CONTACTS NOBODY. Deletes one of the organisation's CUSTOM dispositions.\n\nThe gap `voice_router` named as deliberately absent - \"voice's own\ndispositions router never exposed a delete endpoint\" - which is no longer\ntrue: it does, and this publishes it.\n\nREFUSED WITH 409 IF ANY CALL IS ALREADY DISPOSITIONED WITH IT. So this\nonly ever removes an unused value - history cannot be rewritten by it, and\na 409 means \"this one is in use\", not \"try again\".\n\nThe organisation is carried in a HEADER, not the path, and voice resolves\nthe row with it (`_load_disposition_for_org`). It is the key's own org, so\none tenant cannot delete another's vocabulary by guessing an id.\n\nADMIN ONLY, and that gate is declared HERE. Voice declares\n`require_org_admin()` on its own route, and for a server-to-server call\nthat dependency finds no bearer token and - with\n`ENFORCE_VOICE_PERMISSIONS` off, which is everywhere today - ALLOWS the\nrequest. `require_org_admin` from `developer_api.dependencies.admin` is\nthe one actually protecting this, and it refuses machine keys outright:\ndeleting shared org vocabulary needs a personal key held by an Admin or\nOwner.","operationId":"delete_custom_disposition_dialer_dispositions__disposition_id__delete","parameters":[{"name":"disposition_id","in":"path","required":true,"schema":{"type":"integer","description":"Custom disposition id.","title":"Disposition Id"},"description":"Custom disposition id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/sessions/driver-lease":{"put":{"tags":["Dialer"],"summary":"Put Driver Lease","description":"CONTACTS NOBODY. Grant, refresh or take over YOUR dialer driver lease.\n\nOnly one client at a time may drive a user's dialer. Call this on a timer from the\nclient that is driving; `takeover: true` moves the lease from another client of the\nSAME user. Personal key only: the lease belongs to the key's own user.","operationId":"put_driver_lease_dialer_sessions_driver_lease_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DriverLeaseRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Dialer"],"summary":"Delete Driver Lease","description":"CONTACTS NOBODY. Release YOUR driver lease, only if `client_id` is the current holder.\n\nAnswers `{released: true|false}`; releasing a lease someone else holds is a no-op.","operationId":"delete_driver_lease_dialer_sessions_driver_lease_delete","parameters":[{"name":"client_id","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":64,"pattern":"^[A-Za-z0-9_-]+$","description":"The client releasing its lease.","title":"Client Id"},"description":"The client releasing its lease."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/sessions/presence/desktop":{"put":{"tags":["Dialer"],"summary":"Put Desktop Presence","description":"CONTACTS NOBODY. Heartbeat that says YOUR native desktop dialer is online.\n\nPersonal key only. Send it on a timer while the desktop client runs.","operationId":"put_desktop_presence_dialer_sessions_presence_desktop_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Dialer"],"summary":"Delete Desktop Presence","description":"CONTACTS NOBODY. Clear YOUR desktop presence (the desktop client is closing).","operationId":"delete_desktop_presence_dialer_sessions_presence_desktop_delete","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/sessions/presence":{"get":{"tags":["Dialer"],"summary":"Get Dialer Presence","description":"CONTACTS NOBODY. Is YOUR native desktop dialer online? Personal key only.","operationId":"get_dialer_presence_dialer_sessions_presence_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/dialer/sessions/{session_id}/number-check":{"get":{"tags":["Dialer"],"summary":"Check Session Number","description":"CONTACTS NOBODY. Pre-dial warning for a number picked by hand.\n\nSays whether the dialer would skip that number and why, and which of the contact's\nnumbers to offer instead. The answer contains the contact's PHONE NUMBERS, so the\ncontact must be visible to the key (404 otherwise, before voice is called); voice\nitself only checks that the session belongs to the key's organisation. Advisory:\nany problem answers \"no warning\".","operationId":"check_session_number_dialer_sessions__session_id__number_check_get","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"Session id.","title":"Session Id"},"description":"Session id."},{"name":"contact_id","in":"query","required":true,"schema":{"type":"integer","description":"Contact primary key (`mashup_contacts.id`) in this session's list.","title":"Contact Id"},"description":"Contact primary key (`mashup_contacts.id`) in this session's list."},{"name":"phone_field","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":64,"description":"Which of the contact's phone fields the rep picked.","title":"Phone Field"},"description":"Which of the contact's phone fields the rep picked."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/calls/{livekit_room_name}/disposition/undo":{"post":{"tags":["Dialer"],"summary":"Undo Call Disposition","description":"CONTACTS NOBODY. Undo an AUTO-LOGGED call outcome: the question re-opens for the rep.\n\n409 when the outcome was not auto-logged (a rep's own click is changed with a new\n`PATCH .../disposition`, not undone). Undoing an already-undone outcome succeeds, so a\ndouble tap is safe. A call of another organisation is the same 404 as a missing one;\nthe organisation comes from the key, never the request.","operationId":"undo_call_disposition_dialer_parallel_calls_calls__livekit_room_name__disposition_undo_post","parameters":[{"name":"livekit_room_name","in":"path","required":true,"schema":{"type":"string","description":"Room name of the call.","title":"Livekit Room Name"},"description":"Room name of the call."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/dispositions/settings":{"get":{"tags":["Dialer"],"summary":"Get Dialer Settings","description":"CONTACTS NOBODY. The organisation's dialer settings: auto-disposition, live coach, live transcription.\n\nAn organisation that never changed a setting reports everything off.","operationId":"get_dialer_settings_dialer_dispositions_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Dialer"],"summary":"Update Dialer Settings","description":"CONTACTS NOBODY. Change the organisation's dialer settings. ADMIN ONLY.\n\nThese flags decide whether the organisation's call transcripts are sent to\nthird-party providers (live coach, transcription, automatic outcome logging), so the\norganisation is the key's own and a personal key held by an Admin or Owner is required\n(`require_org_admin` refuses machine keys; voice's own admin gate cannot see an API\nkey). Only the fields sent change; an empty body is a 422.","operationId":"update_dialer_settings_dialer_dispositions_settings_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DialerOrgSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/dispositions/auto-disposition/accuracy":{"get":{"tags":["Dialer"],"summary":"Get Auto Disposition Accuracy","description":"CONTACTS NOBODY. How often automatically logged outcomes were undone or changed, by reason. ADMIN ONLY.\n\nCounts for the key's own organisation only.","operationId":"get_auto_disposition_accuracy_dialer_dispositions_auto_disposition_accuracy_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Look-back window in days.","default":30,"title":"Days"},"description":"Look-back window in days."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_DialerPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/agents/{agent_id}/skill-stats":{"get":{"tags":["Voice"],"summary":"Run statistics for an agent's skills","description":"SPENDS NOTHING. Executions, success rate, duration, tokens and cost\nacross every skill attached to the agent, over the window.","operationId":"get_agent_skill_stats_voice_agents__agent_id__skill_stats_get","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Voice agent id.","title":"Agent Id"},"description":"Voice agent id."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Look-back window in days.","default":30,"title":"Days"},"description":"Look-back window in days."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/agents/{agent_id}/activity":{"get":{"tags":["Voice"],"summary":"An agent's activity feed","description":"SPENDS NOTHING. Calls (with transcripts and recordings), skill runs and\nworkflow runs involving the agent, plus summary counts.","operationId":"get_agent_activity_voice_agents__agent_id__activity_get","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Voice agent id.","title":"Agent Id"},"description":"Voice agent id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Maximum rows per activity type.","default":50,"title":"Limit"},"description":"Maximum rows per activity type."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Look-back window in days.","default":30,"title":"Days"},"description":"Look-back window in days."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/agent-templates":{"get":{"tags":["Voice"],"summary":"Agent templates","description":"SPENDS NOTHING. graph8's templates and this organisation's saved ones;\ninstantiate one with `POST /voice/agents/clone`. A GET here: voice's POST\ncarries only filters.","operationId":"list_agent_templates_voice_agent_templates_get","parameters":[{"name":"entity_type","in":"query","required":false,"schema":{"anyOf":[{"enum":["agent","twin"],"type":"string"},{"type":"null"}],"description":"Only agents, or only twins.","title":"Entity Type"},"description":"Only agents, or only twins."},{"name":"include_system_templates","in":"query","required":false,"schema":{"type":"boolean","description":"Include graph8's own templates.","default":true,"title":"Include System Templates"},"description":"Include graph8's own templates."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/agent-phone-numbers":{"get":{"tags":["Voice"],"summary":"Numbers free to give an agent, and numbers already given","description":"SPENDS NOTHING. The organisation's AI-capable numbers split into\n`available_numbers` and `booked_numbers` (with the agent holding each).\nDialer-only numbers are excluded: they have no SIP trunk to answer on.","operationId":"list_agent_phone_numbers_voice_agent_phone_numbers_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/agents/{agent_id}/documents":{"get":{"tags":["Voice"],"summary":"An agent's documents","description":"SPENDS NOTHING. Documents uploaded with `POST /voice/agents/{agent_id}/\ndocuments/upload`; delete one with `DELETE /voice/agent-documents/{id}`.","operationId":"list_agent_documents_voice_agents__agent_id__documents_get","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Voice agent id.","title":"Agent Id"},"description":"Voice agent id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/agents/{agent_id}/documents/search":{"post":{"tags":["Voice"],"summary":"Search an agent's documents","description":"SPENDS NOTHING billable. The chunks the agent would retrieve for `query`.\nVoice binds form fields, so the body is re-encoded as form data.","operationId":"search_agent_documents_voice_agents__agent_id__documents_search_post","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Voice agent id.","title":"Agent Id"},"description":"Voice agent id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgentDocumentSearch"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/twins":{"get":{"tags":["Voice"],"summary":"The organisation's twins","description":"SPENDS NOTHING. Every twin (a personalised agent modelled on a person)\nwith its persona, identity and knowledge summary.","operationId":"list_twins_voice_twins_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"},"post":{"tags":["Voice"],"summary":"Create a twin","description":"SPENDS CREDITS when a writing sample is attached: voice analyses it with\na paid model and charges the organisation. Multipart because voice binds\nevery field as a form field so the optional sample can travel with them.","operationId":"create_twin_voice_twins_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_create_twin_voice_twins_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}/folders":{"post":{"tags":["Voice"],"summary":"Create a folder in a collection","description":"SPENDS NOTHING. An empty folder uploads can target with `folder_path`.\n404 unless the collection is this organisation's (checked first).","operationId":"create_collection_folder_voice_collections__collection_id__folders_post","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CollectionFolder"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Voice"],"summary":"Delete a folder and everything in it","description":"SPENDS NOTHING. IRREVERSIBLE: removes the folder's files from storage,\nthe database and the vector index, so agents stop answering from them.\n\nOwnership is checked FIRST: voice's handler selects the files by\ncollection id alone, so without this a guessed id would reach another\ntenant's files. Another tenant's collection is a 404.","operationId":"delete_collection_folder_voice_collections__collection_id__folders_delete","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"folder_path","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":512,"description":"The folder; subfolders go too.","title":"Folder Path"},"description":"The folder; subfolders go too."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"voice:delete","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}/stats":{"get":{"tags":["Voice"],"summary":"File statistics for a collection","description":"SPENDS NOTHING. File count and bytes, read from the organisation's own\nstorage prefix (a collection id that is not yours reads as empty).","operationId":"get_collection_stats_voice_collections__collection_id__stats_get","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}/sync":{"post":{"tags":["Voice"],"summary":"Reconcile a collection's records with its stored files","description":"SPENDS NOTHING. Drops records whose file is gone and adds records for\nfiles that have none. Try `dry_run=true` first. Voice 404s another\ntenant's collection. (The every-organisation `sync/all` is not published.)","operationId":"sync_collection_voice_collections__collection_id__sync_post","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"dry_run","in":"query","required":false,"schema":{"type":"boolean","description":"Report what would change without changing it.","default":false,"title":"Dry Run"},"description":"Report what would change without changing it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/voice/collections/search":{"post":{"tags":["Voice"],"summary":"Search across collections","description":"SPENDS NOTHING billable. Vector search over the named collections,\nbest match first. Ids that are not this organisation's are skipped by\nvoice; if none remain it is a 404.","operationId":"search_collections_voice_collections_search_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CollectionSearch"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/voice/collections/{collection_id}/scrape-sources/{source_id}/run":{"post":{"tags":["Voice"],"summary":"Scrape a source now","description":"SPENDS CREDITS. Starts a crawl of the source's site now and indexes what\nit finds, outside its schedule. Voice rate-limits this as expensive.","operationId":"run_scrape_source_voice_collections__collection_id__scrape_sources__source_id__run_post","parameters":[{"name":"collection_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Collection id.","title":"Collection Id"},"description":"Collection id."},{"name":"source_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Scrape source id.","title":"Source Id"},"description":"Scrape source id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/call-scripts/generate":{"post":{"tags":["Voice"],"summary":"Generate a call script for one contact","description":"SPENDS CREDITS. A persona-driven script, retrieving from the agent's\nknowledge and its memory of the contact. Nothing is called or sent.","operationId":"generate_call_script_voice_call_scripts_generate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CallScriptGenerate"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/email-agent/batch":{"post":{"tags":["Voice"],"summary":"Draft many emails in one call","description":"SPENDS CREDITS, once per email. Composes and/or drafts replies in\nparallel; results come back per item even when some fail. Writes, does\nNOT send.","operationId":"batch_email_agent_voice_email_agent_batch_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BatchEmailProcessing"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/voice/mcp-servers/{mcp_server_id}/test":{"post":{"tags":["Voice"],"summary":"Test the connection to a saved MCP server","description":"REACHES OUTSIDE GRAPH8. Connects to the server the organisation saved and\ncounts its tools. (Testing an UNSAVED server is not published: it takes a\ncaller-supplied URL or command.)","operationId":"test_mcp_server_voice_mcp_servers__mcp_server_id__test_post","parameters":[{"name":"mcp_server_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Saved MCP server id.","title":"Mcp Server Id"},"description":"Saved MCP server id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"voice:run","x-graph8-lifecycle":"active"}},"/dialer/sessions/{session_id}":{"get":{"tags":["Voice"],"summary":"One dialer session","description":"SPENDS NOTHING. The session, its live call state and queue counts.\nAnother tenant's session is the same 404 as a missing one.","operationId":"get_dialer_session_dialer_sessions__session_id__get","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Dialer session id.","title":"Session Id"},"description":"Dialer session id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/dialer/sessions/{session_id}/stop":{"post":{"tags":["Voice"],"summary":"Stop a dialer session","description":"SPENDS NOTHING. HANGS UP every live call in the session and completes\nit. Ownership is checked first: voice's handler does not.","operationId":"stop_dialer_session_dialer_sessions__session_id__stop_post","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Dialer session id.","title":"Session Id"},"description":"Dialer session id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/sessions/{session_id}/pause":{"post":{"tags":["Voice"],"summary":"Pause a dialer session","description":"SPENDS NOTHING. Stops auto-advancing and HANGS UP the session's active\ncalls; `POST /dialer/sessions/{session_id}/next-batch` dials on.\nOwnership is checked first: voice's handler does not.","operationId":"pause_dialer_session_dialer_sessions__session_id__pause_post","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Dialer session id.","title":"Session Id"},"description":"Dialer session id."},{"name":"user_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"The rep pausing, for the session log.","title":"User Email"},"description":"The rep pausing, for the session log."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/settings/{user_email}":{"get":{"tags":["Voice"],"summary":"A rep's dialer settings","description":"SPENDS NOTHING. Voicemail skipping, dial-tree skipping, grace period,\npower or parallel mode and line count. Defaults when none are saved.","operationId":"get_dialer_settings_dialer_settings__user_email__get","parameters":[{"name":"user_email","in":"path","required":true,"schema":{"type":"string","minLength":3,"description":"The rep.","title":"User Email"},"description":"The rep."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/dialer/settings":{"put":{"tags":["Voice"],"summary":"Change a rep's dialer settings","description":"SPENDS NOTHING. PATCH semantics: only fields sent change. Takes effect on\nthe rep's next dial.","operationId":"update_dialer_settings_dialer_settings_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DialerSettingsUpdate"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"voice:write","x-graph8-lifecycle":"active"}},"/dialer/dispositions/{disposition_id}/usage":{"get":{"tags":["Voice"],"summary":"Whether a custom disposition is in use","description":"SPENDS NOTHING. `in_use` is true once any call carries it - after which\nchanging whether it counts as connected would re-classify past calls.\nOrg admins only, as in the app.","operationId":"get_disposition_usage_dialer_dispositions__disposition_id__usage_get","parameters":[{"name":"disposition_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Custom disposition id.","title":"Disposition Id"},"description":"Custom disposition id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/sessions/{session_id}/calls":{"post":{"tags":["Voice"],"summary":"Call results for chosen contacts in a parallel session","description":"SPENDS NOTHING. A read with a body (the contact ids). Another tenant's\nsession is a 404.","operationId":"lookup_session_calls_dialer_parallel_calls_sessions__session_id__calls_post","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Dialer session id.","title":"Session Id"},"description":"Dialer session id."},{"name":"group_by_contact","in":"query","required":false,"schema":{"type":"boolean","description":"Latest call plus history per contact, or a flat list.","default":true,"title":"Group By Contact"},"description":"Latest call plus history per contact, or a flat list."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SessionCallsLookup"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/dialer/parallel-calls/analytics/dialer-report/export":{"get":{"tags":["Voice"],"summary":"Download the dialer report as a spreadsheet","description":"SPENDS NOTHING. The same figures as `GET /dialer/parallel-calls/analytics/\ndialer-report`, as an XLSX workbook (summary, breakdown, dispositions).","operationId":"export_dialer_report_dialer_parallel_calls_analytics_dialer_report_export_get","parameters":[{"name":"session_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"One session only.","title":"Session Id"},"description":"One session only."},{"name":"user_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"One rep only.","title":"User Email"},"description":"One rep only."},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"YYYY-MM-DD.","title":"Date From"},"description":"YYYY-MM-DD."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"YYYY-MM-DD.","title":"Date To"},"description":"YYYY-MM-DD."},{"name":"aggregation","in":"query","required":false,"schema":{"enum":["daily","total"],"type":"string","description":"Per-day rows, or one summary.","default":"daily","title":"Aggregation"},"description":"Per-day rows, or one summary."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet":{}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/workflows/node-types/schema":{"get":{"tags":["Workflows"],"summary":"Catalog of all workflow node types and their config schemas","description":"Catalog every node type with its config schema, trigger output schemas,\nresolver-tool hints, and worked examples. Cached (LRU + 1h Cache-Control)\non voice's side - context-cheap to call repeatedly from MCP clients.","operationId":"get_node_types_schema_workflows_node_types_schema_get","parameters":[{"name":"detail","in":"query","required":false,"schema":{"type":"string","pattern":"^(slim|full)$","description":"\"slim\" returns name+type per field; \"full\" includes Pydantic JSON schema.","default":"slim","title":"Detail"},"description":"\"slim\" returns name+type per field; \"full\" includes Pydantic JSON schema."},{"name":"node_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"If provided, return just one entry instead of the full catalog.","title":"Node Type"},"description":"If provided, return just one entry instead of the full catalog."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Get Node Types Schema Workflows Node Types Schema Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows":{"get":{"tags":["Workflows"],"summary":"List workflows for the caller's org","description":"List workflow actions (``runtime_type='workflow'``) owned by the org.\n\nVoice's underlying ``GET /list/{org_id}`` lists all actions; we pin\n``runtime_type=workflow`` so the public surface returns workflows\nonly. Raw action listing (LLM/API/script skills) is intentionally\nnot exposed here.","operationId":"list_workflows_workflows_get","parameters":[{"name":"enabled","in":"query","required":false,"schema":{"anyOf":[{"type":"boolean"},{"type":"null"}],"description":"Filter by enabled flag.","title":"Enabled"},"description":"Filter by enabled flag."},{"name":"category","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by category.","title":"Category"},"description":"Filter by category."},{"name":"is_template","in":"query","required":false,"schema":{"anyOf":[{"type":"boolean"},{"type":"null"}],"description":"Templates only when true.","title":"Is Template"},"description":"Templates only when true."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Workflows Workflows Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"},"post":{"tags":["Workflows"],"summary":"Create a workflow","description":"Create a new workflow. Pins ``org_id`` and ``runtime_type='workflow'``\nserver-side - the body cannot override either.\n\nThe workflow's OWNER is the authenticated caller, never a body field: a\nbody ``created_by`` is dropped (see ``voice_owner_headers``). Record steps\nand record triggers run with the owner's record access, so the key must hold\nthe object scopes they exercise (403 ``missing_scopes``). A node or trigger\nconfig that carries the same key in snake_case and camelCase with values\nthat disagree is refused (422 ``conflicting_node_keys``): keep one spelling.\n\nTranslates the public ``config`` field to voice's internal\n``skill_config`` before forwarding (see module docstring).","operationId":"create_workflow_workflows_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Workflow create payload (voice ActionCreateRequest).","title":"Body"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Create Workflow Workflows Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/workflows/mcp-servers":{"get":{"tags":["Workflows"],"summary":"List MCP servers connected to the org (resolver helper)","description":"Return MCP servers (with their tool lists) for ``tool.mcp_server_id`` resolution.\n\n``org_id`` is REQUIRED by voice (``voice/graph8_livekit/routers/mcp_servers.py``\ndeclares ``list_mcp_servers(org_id: str)`` with no default), so omitting it makes\nvoice answer 422, not an empty list. This route previously sat below the\n``/{action_id}`` catch-all and was unreachable, which hid the missing parameter -\nun-shadowing it turned a 404 into a 422 until this was fixed.\n\nThe org is pinned from the authenticated caller and is never read from the request,\nso a client cannot enumerate another tenant's MCP servers.","operationId":"list_mcp_servers_workflows_mcp_servers_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Mcp Servers Workflows Mcp Servers Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/dispositions":{"get":{"tags":["Workflows"],"summary":"List valid call disposition values (system + this org's custom)","description":"Return every disposition value accepted by ``disposition_filters`` on the\n``new_call_disposition`` trigger - system values AND the caller org's own\ncustom dispositions.\n\nEach entry carries ``origin``: ``system`` for the built-in vocabulary,\n``custom`` for an org-defined one (whose ``value`` is the stored\n``custom_{id}`` key, never the display name). ``category`` keeps its\nexisting meaning: ``sdr_selectable`` a rep can pick it, ``system_set`` only\nthe dialer backend writes it.\n\nAuthority for the system half is voice's ``SDR_SELECTABLE_DISPOSITIONS``\n(``voice/graph8_livekit/schemas/dispositions.py``) plus the two system-set\nvalues the dialer also emits (``sdr_hangup``, ``failed``). That half is\ninlined here and a parity test\n(``developer_api/tests/test_workflow_dispositions.py``) fails the build if\nvoice adds a value that is not mirrored - the previous \"mirror the change\nhere\" comment was not enforced and silently went stale when ``busy`` was\nadded.\n\nThe custom half comes from voice's ``GET /api/dialer/dispositions/{org_id}``,\nwith the org pinned server-side from the authenticated caller and echoed in\nthe ``X-Org-Id`` header voice's tenant gate requires. Nothing about the\nrequest body or query can influence which org is read.\n\nDegraded mode: if voice is unreachable or errors, this returns the system\nvocabulary alone with ``source='static_fallback'`` and logs a warning,\nrather than failing the whole call. An agent that sees\n``source='static_fallback'`` should say it could not confirm custom\ndispositions instead of asserting none exist.\n\nLegacy aliases (``positive``/``neutral``/``negative``) are deliberately\nabsent: ``normalize_disposition`` rewrites them before storage, so a filter\non them could never match.","operationId":"list_dispositions_workflows_dispositions_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Dispositions Workflows Dispositions Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/inbox-tags":{"get":{"tags":["Workflows"],"summary":"List AI Inbox tags for the org (resolver helper)","description":"Resolve human tag descriptions (\"out of office\", \"interested\", \"referred\nme to a colleague\") into the concrete tag IDs required by the\n``new_inbox_tag_set`` trigger's ``tag_filters``.\n\nThis is the resolver that makes reply-intent workflows authorable. Without\nit an agent has no way to turn a tag NAME into a tag ID, so it falls back to\na ``new_email_reply`` trigger plus a condition node grepping the body text -\nwhich is both fragile and duplicates work the inbox AI agent already did\nwhen it tagged the message on arrival.\n\n``ai_applicable_only=true`` narrows to tags whose ``ai_can_apply`` is set,\ni.e. the ones an agent applies automatically the moment an email lands.\nThose are the tags a ``new_inbox_tag_set`` trigger will actually fire on\nwithout a human touching anything.\n\nCalls the ``ai_inbox`` tag service in-process (no voice round-trip). Org is\npinned from the authenticated caller and used as the Postgres tenant schema;\nnothing client-supplied selects the tenant.\n\nReturns ``{tags: [{id, name, description, color, ai_can_apply}], total}``.","operationId":"list_inbox_tags_workflows_inbox_tags_get","parameters":[{"name":"ai_applicable_only","in":"query","required":false,"schema":{"type":"boolean","description":"Return only tags an AI agent is allowed to apply automatically.","default":false,"title":"Ai Applicable Only"},"description":"Return only tags an AI agent is allowed to apply automatically."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Inbox Tags Workflows Inbox Tags Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/workbenches":{"get":{"tags":["Workflows"],"summary":"List workbenches for the org (resolver helper)","description":"Resolve a workbench NAME into the `workbench_id` the workbench nodes need.\n\nReturns ``{workbenches: [{workbench_id, name, entity_type, description,\nrow_count, created_at}], total, page, limit}``.\n\n``workbench_id`` is the value to paste straight into a node config. It is the\nsame id the Workbench page URL shows, so an agent and a human are naming the\nsame thing.\n\nOrg is pinned from the authenticated caller and used as the tenant scope;\nnothing client-supplied selects the tenant.","operationId":"list_workbenches_workflows_workbenches_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Page size.","default":50,"title":"Limit"},"description":"Page size."},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"1-based page number.","default":1,"title":"Page"},"description":"1-based page number."},{"name":"filter_name","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Case-insensitive name filter.","title":"Filter Name"},"description":"Case-insensitive name filter."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Workbenches Workflows Workbenches Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"},"post":{"tags":["Workflows"],"summary":"Create a workbench (so a workflow has somewhere to write)","description":"Create an empty workbench and return its `workbench_id`.\n\nThe missing half of the loop: an agent could be TOLD a workbench id but could\nnever make one, so \"build me a workflow that collects X into a new workbench\"\nalways needed a human to go and click New Workbench first.\n\n``entity_type`` is optional and must be ``contact`` or ``company`` when given;\na blank workbench may defer it, which is what the underlying command already\nallows. ``created_by`` is the authenticated caller and is never read from the\nrequest, so a key cannot attribute a workbench to someone else.\n\nThe webhook API key the browser route returns on create is deliberately NOT\nsurfaced here. It is a write credential for a different ingestion path, it is\nreturned exactly once, and nothing in the workflow surface needs it — an agent\nthat never sees it cannot leak it into a workflow config or a chat transcript.","operationId":"create_workbench_workflows_workbenches_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"{name, entity_type?, description?}","title":"Body"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Create Workbench Workflows Workbenches Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/workflows/executions":{"get":{"tags":["Workflows"],"summary":"List workflow executions for the caller's org (recover a lost execution_id)","description":"List this org's workflow executions, newest first, with SQL-side\npagination - the recovery path for a lost ``execution_id`` (the single\n``GET /workflows/executions/{execution_id}`` read below needs an id you\nno longer have).\n\nOrg is pinned server-side from the authenticated caller and passed to\nvoice in the PATH; a client-supplied ``org_id`` query param is ignored,\nso one tenant can never list another tenant's executions (the voice\nbacking route trusts its path ``org_id``, so pinning here is the tenant\nboundary - getting it wrong is a cross-org IDOR). ``runtime_type`` is\npinned to ``workflow`` so only workflow runs surface here, matching the\nsibling ``GET /workflows`` which does not expose raw LLM/API/script\naction runs.\n\nProxies voice's ``GET /api/v1/executions/list/{org_id}`` and returns its\n``ExecutionListResponse`` shape unchanged - ``{executions: [...],\ntotal_count: int}`` - consistent with this router's pass-through\nconvention (voice owns the execution DTO; re-declaring its ~20 fields\nhere would only drift). Voice also clamps ``limit`` to 1..200 SQL-side;\nthe bounds here reject an out-of-range page with a clean 422 before the\nround-trip.\n\nRead-only and additive: nothing is created, and no existing route changes.","operationId":"list_workflow_executions_workflows_executions_get","parameters":[{"name":"action_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter to a single workflow's executions.","title":"Action Id"},"description":"Filter to a single workflow's executions."},{"name":"status_filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by execution status (equality match — one status per call). The backend writes seven values: pending|running|completed|failed|paused|pending_approval|stopped. The four terminal-or-early states are pending, running, completed, failed; paused and pending_approval are resumable, stopped is terminal.","title":"Status Filter"},"description":"Filter by execution status (equality match — one status per call). The backend writes seven values: pending|running|completed|failed|paused|pending_approval|stopped. The four terminal-or-early states are pending, running, completed, failed; paused and pending_approval are resumable, stopped is terminal."},{"name":"triggered_by","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by the identity that started the run (user email, agent id, 'api', ...).","title":"Triggered By"},"description":"Filter by the identity that started the run (user email, agent id, 'api', ...)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Page size (1..200).","default":50,"title":"Limit"},"description":"Page size (1..200)."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Rows to skip for pagination.","default":0,"title":"Offset"},"description":"Rows to skip for pagination."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Workflow Executions Workflows Executions Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/{action_id}":{"get":{"tags":["Workflows"],"summary":"Get a workflow's full graph","description":"Return the full workflow graph (nodes + edges + trigger config).\n\nTranslates voice's internal ``skill_config`` field to public\n``config`` on the way out (see module docstring).","operationId":"get_workflow_workflows__action_id__get","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Workflow action_id.","title":"Action Id"},"description":"Workflow action_id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Get Workflow Workflows  Action Id  Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"},"put":{"tags":["Workflows"],"summary":"Update a workflow's graph","description":"Update a workflow. The voice update endpoint takes ``org_id`` as a\nquery param and the partial body in JSON, so we forward both. A graph with\nrecord steps or a record trigger needs the object scopes they exercise\n(403 ``missing_scopes``), like create, and a node or trigger config whose\nsnake_case and camelCase keys disagree is refused (422\n``conflicting_node_keys``). On a workflow with record steps or a record\ntrigger, only its owner or a graph8 admin may change what it runs (403\n``owner_or_admin_required``); its name and description stay editable.\n\nTranslates the public ``config`` field to voice's internal\n``skill_config`` before forwarding (see module docstring).","operationId":"update_workflow_workflows__action_id__put","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Workflow action_id.","title":"Action Id"},"description":"Workflow action_id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Partial update payload (voice ActionUpdateRequest).","title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Update Workflow Workflows  Action Id  Put"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Workflows"],"summary":"Delete a workflow","description":"Delete a workflow. Voice's delete returns ``{\"success\": true, ...}``\non success and 403 for system defaults - both pass through.","operationId":"delete_workflow_workflows__action_id__delete","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Workflow action_id.","title":"Action Id"},"description":"Workflow action_id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Delete Workflow Workflows  Action Id  Delete"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"workflows:delete","x-graph8-lifecycle":"active"}},"/workflows/{action_id}/trigger-status":{"get":{"tags":["Workflows"],"summary":"Trigger status (cursor + config) for a workflow","description":"Return whether the workflow has a trigger, its type, and last cursor.","operationId":"get_trigger_status_workflows__action_id__trigger_status_get","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Workflow action_id.","title":"Action Id"},"description":"Workflow action_id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Get Trigger Status Workflows  Action Id  Trigger Status Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/validate":{"post":{"tags":["Workflows"],"summary":"Validate a workflow graph (structural + reference resolution)","description":"Validate a workflow without saving. Returns errors + warnings +\nmissing_references so an MCP client can repair before retrying create.\n\nThe inner ``config`` is normalized the same way create/update do so\na caller can validate hybrid/ReactFlow shapes and get a clean answer\ninstead of a structural error from a key the validator didn't expect.","operationId":"validate_workflow_workflows_validate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"WorkflowValidateRequest: {config: {nodes, edges, start_node_id}}.","title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Validate Workflow Workflows Validate Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/workflows/plan":{"post":{"tags":["Workflows"],"summary":"Preview a normalized execution plan for an inline workflow graph","description":"Compute a normalized plan for a graph that is NOT yet saved. Accepts\neither ``{config: {...}}`` or a raw graph ``{nodes, edges, start_node_id}``\ndirectly. Read-only: nothing is persisted or executed.","operationId":"plan_inline_workflow_workflows_plan_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"{config: {nodes, edges, ...}, include_cost?, include_audience_size?}","title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Plan Inline Workflow Workflows Plan Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/{action_id}/plan":{"post":{"tags":["Workflows"],"summary":"Preview a normalized execution plan for a saved workflow","description":"Fetch a saved workflow's graph and compute its normalized plan. Org is\npinned server-side; the caller cannot preview another tenant's workflow.\nRead-only.","operationId":"plan_workflow_workflows__action_id__plan_post","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Workflow action_id.","title":"Action Id"},"description":"Workflow action_id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"{include_cost?, include_audience_size?}","title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Plan Workflow Workflows  Action Id  Plan Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/{action_id}/execute":{"post":{"tags":["Workflows"],"summary":"Execute a workflow","description":"Trigger a workflow run. Returns ``execution_id`` for polling.\n\nA workflow with record steps or a record trigger runs them with its OWNER's\nrecord access, and this run's input feeds them: the key must hold the object\nscopes they exercise (403 ``missing_scopes``) and its member must own the\nworkflow or administer the org (403 ``owner_or_admin_required``, from the\nworkflow service, which receives the member as the verified identity). The\nsaved workflow is read before the run so that check is never skipped: when\nit cannot be read, the answer is ``502`` and nothing runs.\n\nPins ``org_id`` server-side; the caller cannot override which org's\nexecution row is created. ``triggered_by`` defaults to the caller's\nuser id when not supplied.\n\nIf the workflow service takes the request but does not answer in time,\nthe answer is ``202`` with ``outcome`` ``started`` (run found, with its\n``execution_id``) or ``unknown`` (check the executions list first), not a\n502: the run may well be going. Send an ``Idempotency-Key`` to make retries\nsafe; a retry with the same key returns the first answer.","operationId":"execute_workflow_workflows__action_id__execute_post","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Workflow action_id.","title":"Action Id"},"description":"Workflow action_id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"ExecutionCreateRequest body.","title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Execute Workflow Workflows  Action Id  Execute Post"}}}},"202":{"description":"The run request reached the workflow service but no reply came back in time. ``outcome`` is ``started`` (the run was found; ``execution_id`` is set) or ``unknown`` (check ``GET /workflows/executions`` before retrying). Never a failure."},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/workflows/{action_id}/trigger-reset":{"post":{"tags":["Workflows"],"summary":"Reset the trigger cursor to now","description":"Stop reprocessing old events - sets the trigger cursor to now().","operationId":"reset_trigger_cursor_workflows__action_id__trigger_reset_post","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Workflow action_id.","title":"Action Id"},"description":"Workflow action_id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Reset Trigger Cursor Workflows  Action Id  Trigger Reset Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/workflows/executions/{execution_id}":{"get":{"tags":["Workflows"],"summary":"Get execution status / result","description":"Return execution status + output_data + token / cost telemetry.\n\nThe MCP polling pattern: call this until ``status`` reaches a TERMINAL\nvalue — ``completed``, ``failed`` or ``stopped``. A run can also sit in\n``paused`` or ``pending_approval`` (both non-terminal and resumable via\nthe lifecycle routes below), so a poller must treat those as \"keep\nwaiting\", not \"done\" — polling only for completed/failed hangs forever on\na paused or approval-gated run. The full set voice writes is\n``pending|running|completed|failed|paused|pending_approval|stopped``.\nVoice's GET enforces tenant isolation natively so no pre-flight is needed\nfor the read path.","operationId":"get_execution_workflows_executions__execution_id__get","parameters":[{"name":"execution_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Execution UUID.","title":"Execution Id"},"description":"Execution UUID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Get Execution Workflows Executions  Execution Id  Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/executions/{execution_id}/pause":{"post":{"tags":["Workflows"],"summary":"Pause a running execution (tenant-checked)","description":"Pause a running workflow execution. Pre-flight enforces that the\nexecution belongs to the caller's org before forwarding to voice.","operationId":"pause_execution_workflows_executions__execution_id__pause_post","parameters":[{"name":"execution_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Execution UUID.","title":"Execution Id"},"description":"Execution UUID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"{reason?, message?}","title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Pause Execution Workflows Executions  Execution Id  Pause Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/workflows/executions/{execution_id}/resume":{"post":{"tags":["Workflows"],"summary":"Resume a paused execution (tenant-checked)","description":"Resume a paused execution. Pre-flight enforces tenant ownership.","operationId":"resume_execution_workflows_executions__execution_id__resume_post","parameters":[{"name":"execution_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Execution UUID.","title":"Execution Id"},"description":"Execution UUID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"{from_step?, skip_failed?}","title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Resume Execution Workflows Executions  Execution Id  Resume Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/workflows/executions/{execution_id}/stop":{"post":{"tags":["Workflows"],"summary":"Permanently stop an execution (tenant-checked)","description":"Stop an execution permanently. Pre-flight enforces tenant ownership.","operationId":"stop_execution_workflows_executions__execution_id__stop_post","parameters":[{"name":"execution_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Execution UUID.","title":"Execution Id"},"description":"Execution UUID."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"{reason?, save_partial_results?, message?}","title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Stop Execution Workflows Executions  Execution Id  Stop Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/workflows/integrations/roam/users":{"get":{"tags":["Workflows"],"summary":"List Roam users connected to the org (resolver helper)","description":"Return Roam users for ``send_roam_notification.user_ids`` resolution.","operationId":"list_roam_users_workflows_integrations_roam_users_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Roam Users Workflows Integrations Roam Users Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/integrations/roam/groups":{"get":{"tags":["Workflows"],"summary":"List Roam groups connected to the org (resolver helper)","description":"Return Roam groups for ``send_roam_notification.recipient_id`` resolution.","operationId":"list_roam_groups_workflows_integrations_roam_groups_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Roam Groups Workflows Integrations Roam Groups Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/integrations/slack/users":{"get":{"tags":["Workflows"],"summary":"List Slack users for the org (resolver helper)","description":"Return Slack workspace users for ``send_slack_notification.user_id`` resolution.","operationId":"list_slack_users_workflows_integrations_slack_users_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Slack Users Workflows Integrations Slack Users Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/integrations/slack/channels":{"get":{"tags":["Workflows"],"summary":"List Slack channels for the org (resolver helper)","description":"Return Slack channels for ``send_slack_notification.channel_id`` resolution.","operationId":"list_slack_channels_workflows_integrations_slack_channels_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Slack Channels Workflows Integrations Slack Channels Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/forms/{form_id}/fields":{"get":{"tags":["Workflows"],"summary":"Discover form field names from recent submissions (resolver helper)","description":"Sample recent submissions for a form and return the unique field names.\n\nUse this to populate the ``form_fields[]`` array on a\n``new_form_submitted`` trigger node config at create time, mirroring\nwhat ``NodeConfigPanel.handleFormSelect`` does on the frontend when\nthe user selects a form in the dropdown.\n\nWithout these names pre-populated, downstream nodes cannot reference\nsubmitted values via ``${<trigger_node_id>.<field>}`` until the user\nre-selects the form in the UI.\n\nCalls ``forms`` handlers in-process (no voice round-trip). Forms data\nlives in ClickHouse via ``apps.forms()`` — sampled submissions are\npaginated server-side; we only ever read ``per_page=10`` here.\n\nReturns ``{form_id, fields: [str], sample_size: int}``. Empty\n``fields`` means no submissions exist yet — the caller should fall\nback to asking the user for the field list, or accept that\n``${trigger.<field>}`` references will only resolve once a real\nsubmission arrives.","operationId":"describe_form_fields_workflows_forms__form_id__fields_get","parameters":[{"name":"form_id","in":"path","required":true,"schema":{"type":"string","description":"HTML form id (form_tag_id)","title":"Form Id"},"description":"HTML form id (form_tag_id)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Describe Form Fields Workflows Forms  Form Id  Fields Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/integrations/linkedin/senders":{"get":{"tags":["Workflows"],"summary":"List LinkedIn sender accounts for the org (resolver helper)","description":"Return LinkedIn sender accounts for ``sender_account_id`` resolution.\n\nResolves the ``sender_account_id`` on the Netrion workflow nodes\n(``send_netrion_connection_request`` / ``send_netrion_message``) and on the\n``linkedin_*`` triggers' ``linkedin_account_id``. Until this existed there was\nNO way to discover these ids programmatically: voice's ``_RESOLVER_HINTS``\nsaid \"no MCP resolver yet — ask user\", and the only listing endpoint\n(``GET /v1/linkedin/accounts``) is behind ``get_current_user`` browser auth,\nso an MCP/API caller could build the node and then not attach a sender.\n\n``sender_account_id`` is the INTEGER PK (``ArlinkLinkedInAccount.id``), which\nis the value the node config takes — deliberately NOT the arlink ``lia_...``\nstring. ``account_resolution.resolve_active_account`` cannot parse the\n``lia_`` form, and the Netrion nodes opt into ``strict_account``, so naming\none is a hard failure rather than a silent send from an arbitrary seat. The\nfield is emitted as a STRING because that is the node config's own type.\n\nMirrors ``GET /v1/linkedin/accounts`` on degradation: flag off, no accounts,\nor per-org tables not provisioned all answer an empty list, never a 500.\nA sender that is not ``status='OK'`` is still returned, with its status, so\nthe caller can say \"that seat is disconnected\" instead of \"no seats\".","operationId":"list_linkedin_senders_workflows_integrations_linkedin_senders_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Linkedin Senders Workflows Integrations Linkedin Senders Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/skills/models":{"get":{"tags":["Skills"],"summary":"List supported LLM model identifiers","description":"Return the static catalog of LLM model ids the create/update\nendpoints accept. Voice ultimately decides which models route to\nwhich provider — this catalog is a hint for MCP clients filling in\nthe ``model`` field of ``g8_skill_create_llm``.","operationId":"list_models_skills_models_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Models Skills Models Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/skills/templates":{"get":{"tags":["Skills"],"summary":"List skill templates","description":"List skill templates available in the caller's org plus shared\nsystem templates. Workflow templates are filtered out client-side.\n\nVoice's ``GET /templates/{org_id}/list`` returns all template rows\n(including workflow templates). We filter post-fetch so the public\nsurface stays sealed to skills only.","operationId":"list_templates_skills_templates_get","parameters":[{"name":"category","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by category.","title":"Category"},"description":"Filter by category."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Templates Skills Templates Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/skills":{"get":{"tags":["Skills"],"summary":"List skills (LLM + API) for the caller's org","description":"List skills owned by the org. When ``runtime_type`` is omitted we\nmake two voice calls (one for llm, one for api) and merge the results,\nso the public surface always returns just the two allowed runtimes\nand never leaks workflows/scripts even if voice's filter logic drifts.","operationId":"list_skills_skills_get","parameters":[{"name":"runtime_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^(llm|api)$"},{"type":"null"}],"description":"Filter to a single runtime (llm or api). Omit to see both.","title":"Runtime Type"},"description":"Filter to a single runtime (llm or api). Omit to see both."},{"name":"enabled","in":"query","required":false,"schema":{"anyOf":[{"type":"boolean"},{"type":"null"}],"description":"Filter by enabled flag.","title":"Enabled"},"description":"Filter by enabled flag."},{"name":"category","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by category.","title":"Category"},"description":"Filter by category."},{"name":"object_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string","pattern":"^(Company|Contact|Deal|Campaign)$"},{"type":"null"}],"description":"Filter by entity type the skill targets.","title":"Object Type"},"description":"Filter by entity type the skill targets."},{"name":"include_system","in":"query","required":false,"schema":{"type":"boolean","description":"Include shared system-default skills alongside org-owned ones.","default":true,"title":"Include System"},"description":"Include shared system-default skills alongside org-owned ones."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response List Skills Skills Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"},"post":{"tags":["Skills"],"summary":"Create a skill (LLM or API runtime)","description":"Create a new skill. Pins ``org_id`` server-side and rejects any\nruntime_type other than ``llm`` or ``api``.\n\nBody must include ``name``, ``runtime_type`` (``llm`` or ``api``),\nand the matching ``llm_config`` or ``api_config`` block.\n\nThis is the SAME endpoint that ``g8_skill_create_from_node`` (lift)\nroutes through, so lifted skills are byte-identical to authored ones.","operationId":"create_skill_skills_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Skill create payload (voice ActionCreateRequest).","title":"Body"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Create Skill Skills Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/skills/{action_id}":{"get":{"tags":["Skills"],"summary":"Get a skill's full configuration","description":"Return the full skill record (llm_config / api_config + metadata).\n\nReturns 404 for workflow / script rows even if voice has them —\nthe skill surface is sealed.","operationId":"get_skill_skills__action_id__get","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill action_id.","title":"Action Id"},"description":"Skill action_id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Get Skill Skills  Action Id  Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"},"put":{"tags":["Skills"],"summary":"Update a skill","description":"Update an existing skill. Pre-flight GET enforces the action is\nactually a skill (not a workflow/script) before forwarding the PUT.","operationId":"update_skill_skills__action_id__put","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill action_id.","title":"Action Id"},"description":"Skill action_id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Partial update (voice ActionUpdateRequest).","title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Update Skill Skills  Action Id  Put"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Skills"],"summary":"Delete a skill","description":"Delete a skill. Pre-flight GET enforces the target is a skill\nbefore forwarding the DELETE.\n\nNOTE: this is a hard delete at the voice layer. Per the PRD lock,\nthe skills surface does NOT do MCP-only soft-delete reference checks\nhere — that logic lives in the MCP tool layer (where we can read\nworkflow node references and refuse the delete).","operationId":"delete_skill_skills__action_id__delete","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill action_id.","title":"Action Id"},"description":"Skill action_id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Delete Skill Skills  Action Id  Delete"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"workflows:delete","x-graph8-lifecycle":"active"}},"/skills/{action_id}/variables":{"get":{"tags":["Skills"],"summary":"Extract {variable} placeholders from a skill's templates","description":"Return the deduplicated, first-seen-order list of ``{variable}``\nplaceholders extracted from the skill's templates.\n\nFor LLM skills we scan ``llm_config.prompt_template``.\nFor API skills we scan ``api_config.endpoint``, ``api_config.body_template``,\nevery header value, and every query param value.\n\nSingle-brace regex only — ``{{double_brace}}`` patterns are ignored\nto avoid pulling Jinja control structures out as variables.","operationId":"extract_variables_skills__action_id__variables_get","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill action_id.","title":"Action Id"},"description":"Skill action_id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Extract Variables Skills  Action Id  Variables Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/skills/validate":{"post":{"tags":["Skills"],"summary":"Validate a skill template (extract + warn on common mistakes)","description":"Dry-run template validator. Returns extracted variables plus\nwarnings about common mistakes (double-brace usage, unmatched braces).\n\nPer the PRD lock (Q3): warn-only. We never block creation on warnings\nhere — the user is the source of truth and a double-brace pattern is\nvalid Jinja that voice's runtime may handle differently from skills.\n\nAccepts two shapes:\n  1) ``{\"template\": \"Hello {name}\"}`` — one string in, vars out.\n  2) ``{\"runtime_type\": \"llm\", \"llm_config\": {...}}`` — full skill\n     shape, scans every template field the matching runtime would use.","operationId":"validate_template_skills_validate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Template validation payload. ``{template: str}`` or ``{runtime_type, llm_config|api_config}``.","title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Validate Template Skills Validate Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/skills/from-template":{"post":{"tags":["Skills"],"summary":"Create a skill from a template","description":"Instantiate a skill from a template. Forwards to voice's\n``POST /from-template/{template_id}`` with the caller's org_id pinned.\n\nPost-creation we re-fetch the new action and 404 if the resulting\nruntime_type is not a skill — guards against templates of workflow\nor script runtime sneaking into the skill surface.","operationId":"create_from_template_skills_from_template_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"``{template_id: str, name: str, overrides?: dict}``","title":"Body"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Create From Template Skills From Template Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/skills/from-node":{"post":{"tags":["Skills"],"summary":"Lift a workflow action node into a standalone skill","description":"Two-step lift (per PRD lock):\n  1) Fetch the workflow + locate the named node.\n  2) Resolve the referenced action_id, fetch its full config, then\n     POST to the SAME ``/api/v1/actions/create`` endpoint with a\n     derived name. The new action_id is returned.\n\nThis is the route ``g8_skill_create_from_node`` MCP tool calls. It\nguarantees lift skills are byte-identical to authored skills.\n\nDoes NOT modify the workflow — the lift is a copy, not a move. If\nthe caller wants the workflow node to reference the new skill, they\nupdate the workflow themselves with ``g8_workflow_update_node``.","operationId":"create_from_node_skills_from_node_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"``{workflow_id: str, node_id: str, name?: str}``. Reads the workflow's action node config and creates a new standalone skill with the same config, then returns the new skill.","title":"Body"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Create From Node Skills From Node Post"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/skills/{action_id}/execute":{"post":{"tags":["Skills"],"summary":"Execute a skill once","description":"Run a skill once and return the execution result.\n\nPre-flight GET enforces the action is a skill (not a workflow) so\nthe skill execute surface stays sealed. ``org_id`` is pinned;\n``triggered_by`` defaults to the caller's user id.","operationId":"execute_skill_skills__action_id__execute_post","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill action_id.","title":"Action Id"},"description":"Skill action_id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"ExecutionCreateRequest body.","title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Execute Skill Skills  Action Id  Execute Post"}}}},"202":{"description":"The run request reached the skill service but no reply came back in time. ``outcome`` is ``started`` (the run was found; ``execution_id`` is set) or ``unknown`` (check ``possible_executions`` before retrying). Never a failure."},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/skills/{action_id}/versions":{"get":{"tags":["Workflows"],"summary":"A skill's versions","description":"SPENDS NOTHING. Version history, newest first, with the published one\nmarked. Compare two with `GET /skills/{action_id}/versions/{version_id}/diff`.","operationId":"list_skill_versions_skills__action_id__versions_get","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill (action) id.","title":"Action Id"},"description":"Skill (action) id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Newest first.","default":50,"title":"Limit"},"description":"Newest first."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/skills/{action_id}/versions/{version_id}/restore":{"post":{"tags":["Workflows"],"summary":"Restore an earlier version of a skill","description":"SPENDS NOTHING. Publishes the old snapshot as a NEW version, live for the\nnext run - agents and workflows using the skill pick it up. Append-only, so\nthe restore can itself be rolled back. Routine-managed skills refuse (403). A\nrestored graph with record steps or a record trigger needs the same object\nscopes as a create or an update (403 ``missing_scopes``), a restored graph\nwhose snake_case and camelCase node keys disagree is refused (422\n``conflicting_node_keys``), and a restore that changes such a workflow's\ngraph is refused (403 ``owner_or_admin_required``) unless the key's member\nowns the workflow or administers the org. The version's graph is read first\nto run those checks: 404 when it cannot be found (unknown skill or version).","operationId":"restore_skill_version_skills__action_id__versions__version_id__restore_post","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill (action) id.","title":"Action Id"},"description":"Skill (action) id."},{"name":"version_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"The version to bring back.","title":"Version Id"},"description":"The version to bring back."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/skills/{action_id}/test":{"post":{"tags":["Workflows"],"summary":"Dry-run a skill once","description":"SPENDS NOTHING. One DRY run from a saved case or ad-hoc inputs: returns\nthe resolved prompt (llm skills) or the unsent request with secrets masked\n(api skills). Never calls a model, never sends, never writes an execution.","operationId":"test_skill_once_skills__action_id__test_post","parameters":[{"name":"action_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"description":"Skill (action) id.","title":"Action Id"},"description":"Skill (action) id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SkillTestRun"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/workflows/executions/approve":{"post":{"tags":["Workflows"],"summary":"Approve a run waiting on a human","description":"REACHES OUTSIDE GRAPH8 when the approved step does: the paused run\nRESUMES and performs the action it was holding (a send, an API call, a\nwrite). 403 when `approved_by` may not approve it; 404 for another\norganisation's run.","operationId":"approve_execution_workflows_executions_approve_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ExecutionApproval"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/workflows/executions/reject":{"post":{"tags":["Workflows"],"summary":"Reject a run waiting on a human","description":"SPENDS NOTHING. The held action is NOT performed and the run ends. For\n\"try again with changes\" use `POST /workflows/executions/request-changes`.","operationId":"reject_execution_workflows_executions_reject_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ExecutionRejection"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"workflows:write","x-graph8-lifecycle":"active"}},"/workflows/stats/executions":{"get":{"tags":["Workflows"],"summary":"Run health for the organisation or one skill","description":"SPENDS NOTHING. Status buckets that sum to the total, success rate,\nduration, tokens, and `total_cost_usd` - a FLOOR on spend, since only\nLLM-runtime runs record a cost (`executions_with_cost` says how many).","operationId":"get_execution_stats_workflows_stats_executions_get","parameters":[{"name":"action_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"One skill's health; omit for the organisation.","title":"Action Id"},"description":"One skill's health; omit for the organisation."},{"name":"days","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","maximum":365,"minimum":1},{"type":"null"}],"description":"Window; omit for lifetime.","title":"Days"},"description":"Window; omit for lifetime."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/stats/trigger-activity":{"get":{"tags":["Workflows"],"summary":"Whether workflow triggers are being evaluated","description":"SPENDS NOTHING. Per workflow: when its trigger was last evaluated and\nlast matched. A workflow absent from the answer is UNKNOWN (never evaluated,\nor its 30-day record lapsed), not \"never ran\".","operationId":"get_trigger_activity_workflows_stats_trigger_activity_get","parameters":[{"name":"action_ids","in":"query","required":true,"schema":{"type":"string","minLength":1,"description":"Comma-separated workflow ids (first 200 used).","title":"Action Ids"},"description":"Comma-separated workflow ids (first 200 used)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"workflows:read","x-graph8-lifecycle":"active"}},"/workflows/integrations/{provider_name}/test":{"post":{"tags":["Workflows"],"summary":"Try a Roam or Slack token","description":"REACHES OUTSIDE GRAPH8. Calls the provider with the token and reports\nwhether it works (`success`, `error`). The token is not stored; save it with\n`PUT /workflows/integrations/{provider_name}`.","operationId":"test_integration_credential_workflows_integrations__provider_name__test_post","parameters":[{"name":"provider_name","in":"path","required":true,"schema":{"enum":["roam","slack"],"type":"string","description":"roam or slack.","title":"Provider Name"},"description":"roam or slack."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/IntegrationCredentialTest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_VoicePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"workflows:run","x-graph8-lifecycle":"active"}},"/work/room":{"get":{"tags":["Work"],"summary":"Get Work Room","description":"The whole Work room this credential may read, in one call.\n\nChannels, conversations, recent messages and events, the member directory\nand the agent roster — narrowed to the caller's own audience and bounded to\nthe recent end of history. ``truncation`` names what was left out and\ncarries the cursor to resume each conversation from at\n``GET /work/conversations/{conversation_id}/messages``.\n\nFor an organisation credential that audience is the built-in channels; see\nthe module docstring for why, and for what it is not.","operationId":"get_work_room_work_room_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkRoom_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/channels":{"get":{"tags":["Work"],"summary":"List Work Channels","description":"The channels this credential may read.\n\nThe cheap half of ``GET /work/room``: membership only, no message or event\nhistory. Decided by ``room_visibility.visible_room`` — the same predicate\nthe room read and the realtime socket run — so a channel can never be listed\nhere and refused there.","operationId":"list_work_channels_work_channels_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelList_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"},"post":{"tags":["Work"],"summary":"Create Work Channel","description":"Create one Work channel.\n\n``409`` when the name is taken — a channel's slug IS its room address, so two\nchannels cannot share one. ``422`` for a name or description that cannot be\nnormalized, and for an unknown ``templateId``. ``templateId`` seats the\ntemplate's specialists and seeds its Canvas.\n\nThe creator comes from the authenticated principal. The body cannot express\nit: ``author``, ``actor_id``, ``org_id`` and ``createdBy`` are refused\noutright rather than ignored.","operationId":"create_work_channel_work_channels_post","parameters":[{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkChannelCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelWriteResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/channels/available":{"get":{"tags":["Work"],"summary":"List Available Work Channels","description":"The organization's channels this credential is not part of.\n\nThe channel browser. An ``open`` channel carries its description and member\ncount; a ``private`` one answers with identity only, so a room nobody here\nbelongs to is listed without leaking anything about it. Built-ins and\narchived channels are absent.","operationId":"list_available_work_channels_work_channels_available_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkAvailableChannelList_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/channels/{channel_id}":{"patch":{"tags":["Work"],"summary":"Update Work Channel","description":"Change one channel's display name, description, visibility, seating, agent policy or archive state.\n\n**Field PRESENCE is the contract** — an omitted field keeps its stored value,\nand ``description: null`` clears it.\n\n``name`` is not accepted and a rename never moves the room: the slug is the\nchannel's address, and changing it would strand every event already filed\nunder the old one. ``403`` when the caller neither owns the channel nor\nholds owner/admin rights, and separately when a non-admin tries to change\nagent activation — an organization-level spend decision rather than a\nroom-owner one. ``409`` for a built-in channel's identity or visibility.","operationId":"update_work_channel_work_channels__channel_id__patch","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Channel id or slug","title":"Channel Id"},"description":"Channel id or slug"},{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkChannelSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelWriteResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Work"],"summary":"Delete Work Channel","description":"Delete one channel for everyone, leaving a non-restorable tombstone.\n\n``confirmationName`` must equal the channel's own slug. This is not\nreversible: the room's history stays as an audit record but nobody can read\nthe channel again. The in-app surface spells this ``POST\n/v1/work/channels/{id}/delete``; the verb here is ``DELETE`` because that is\nwhat the operation is and what the scope derived for it means.","operationId":"delete_work_channel_work_channels__channel_id__delete","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Channel id or slug","title":"Channel Id"},"description":"Channel id or slug"},{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkChannelDeleteRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelWriteResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"work:delete","x-graph8-lifecycle":"active"}},"/work/channels/{channel_id}/purpose":{"put":{"tags":["Work"],"summary":"Set Work Channel Purpose","description":"Give one channel a purpose, taking it from whichever channel held it.\n\n``purpose`` is required but nullable: ``null`` clears it. An empty body is\nrefused rather than guessed, because this operation reassigns state on\nchannels the caller did not name and may not act on an ambiguity —\n``reassignedChannelIds`` says which ones it moved.","operationId":"set_work_channel_purpose_work_channels__channel_id__purpose_put","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Channel id or slug","title":"Channel Id"},"description":"Channel id or slug"},{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkChannelPurposeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelWriteResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/channels/{channel_id}/canvas":{"get":{"tags":["Work"],"summary":"Get Work Channel Canvas","description":"One channel's Canvas, to a caller entitled to that channel.\n\n``403`` when the caller may not read the channel — the same rule that\ndecides its messages, so a room cannot be readable on one half and refused\non the other. A channel with no Canvas answers an empty one rather than 404.","operationId":"get_work_channel_canvas_work_channels__channel_id__canvas_get","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Channel id or slug","title":"Channel Id"},"description":"Channel id or slug"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkCanvas_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"},"post":{"tags":["Work"],"summary":"Save Work Channel Canvas","description":"Replace one channel's Canvas from its content. Signed server-side.\n\nThe counterpart of the published ``GET`` on this path. It is the app's\n``POST`` (bare content, revision authored server-side with the caller's\nderived key), not the ``PUT`` that accepts a client-SIGNED event, which a\nmachine principal has no signing story for.\n\n``baseRevisionId`` is a compare-and-swap: send the ``revisionId`` the\n``GET`` gave you, omit it to skip the check, or send ``\"\"`` to assert no\ncanvas existed. ``403`` when the caller may not edit the channel; ``409``\nfor an archived channel, a replayed key with a different body, or a stale\n``baseRevisionId``.","operationId":"save_work_channel_canvas_work_channels__channel_id__canvas_post","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Channel id or slug","title":"Channel Id"},"description":"Channel id or slug"},{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkCanvasSaveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkCanvas_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/conversations/{conversation_id}/messages":{"get":{"tags":["Work"],"summary":"List Work Conversation Messages","description":"Page one conversation's messages, newest first.\n\nAuthorization happens before a single message is read, and an unreadable id\nand an unknown id produce the same ``403`` on purpose: handing back an empty\npage for a conversation the caller may not see would still confirm it\nexists.","operationId":"list_work_conversation_messages_work_conversations__conversation_id__messages_get","parameters":[{"name":"conversation_id","in":"path","required":true,"schema":{"type":"string","description":"Channel name, channel id, or direct-message id","title":"Conversation Id"},"description":"Channel name, channel id, or direct-message id"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Page size; clamped to the server maximum","default":50,"title":"Limit"},"description":"Page size; clamped to the server maximum"},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Opaque cursor from a previous page","title":"Cursor"},"description":"Opaque cursor from a previous page"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkMessagePage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/conversations/{conversation_id}/events":{"get":{"tags":["Work"],"summary":"List Work Conversation Events","description":"Page one conversation's chat events, newest first.\n\nThe twin of the message page, and not redundant with it: some Work history\nexists only as an event and has no message row at all, so a client told\n``truncation.events`` needs this route to fetch what it lost. Same\nauthorization, same cursor encoding.","operationId":"list_work_conversation_events_work_conversations__conversation_id__events_get","parameters":[{"name":"conversation_id","in":"path","required":true,"schema":{"type":"string","description":"Channel name, channel id, or direct-message id","title":"Conversation Id"},"description":"Channel name, channel id, or direct-message id"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Page size; clamped to the server maximum","default":50,"title":"Limit"},"description":"Page size; clamped to the server maximum"},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Opaque cursor from a previous page","title":"Cursor"},"description":"Opaque cursor from a previous page"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkEventPage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/conversations/{conversation_id}/files":{"get":{"tags":["Work"],"summary":"List Work Conversation Files","description":"The messages in one conversation that carry files, newest first.\n\nShared-file history uses exactly the conversation's live read permissions —\nlosing access to a room loses access to what was shared in it.","operationId":"list_work_conversation_files_work_conversations__conversation_id__files_get","parameters":[{"name":"conversation_id","in":"path","required":true,"schema":{"type":"string","description":"Channel name, channel id, or direct-message id","title":"Conversation Id"},"description":"Channel name, channel id, or direct-message id"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Page size; clamped to the server maximum","default":50,"title":"Limit"},"description":"Page size; clamped to the server maximum"},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Opaque cursor from a previous page","title":"Cursor"},"description":"Opaque cursor from a previous page"},{"name":"query","in":"query","required":false,"schema":{"type":"string","maxLength":200,"description":"Filter by filename","default":"","title":"Query"},"description":"Filter by filename"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkMessagePage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/search":{"get":{"tags":["Work"],"summary":"Search Work","description":"Search everything this credential may read, and nothing else.\n\nDeliberately has no storage-plane branch: \"what can I find\" is a question\nabout one caller's permissions, and there is no viewer whose membership\ncould scope an answer for a credential that has none.","operationId":"search_work_work_search_get","parameters":[{"name":"q","in":"query","required":true,"schema":{"type":"string","minLength":2,"maxLength":200,"description":"Search text","title":"Q"},"description":"Search text"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"description":"Maximum hits; clamped to the server maximum","default":25,"title":"Limit"},"description":"Maximum hits; clamped to the server maximum"},{"name":"conversation","in":"query","required":false,"schema":{"anyOf":[{"type":"string","minLength":1,"maxLength":200},{"type":"null"}],"description":"Channel name or direct-message id to search within","title":"Conversation"},"description":"Channel name or direct-message id to search within"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkSearchResults_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/attachments/{attachment_id}":{"get":{"tags":["Work"],"summary":"Get Work Attachment Link","description":"Authorize this credential for one attachment, then mint a short-lived link.\n\nBeing authenticated is not permission: an attachment id is a UUID in a URL,\nand \"holds a key\" would otherwise make every file in the organization\nreadable. A caller may read an attachment carried by a message in a\nconversation they can see. A missing attachment and an unreadable one both\nanswer ``404``, so this cannot be used to probe which ids exist.","operationId":"get_work_attachment_link_work_attachments__attachment_id__get","parameters":[{"name":"attachment_id","in":"path","required":true,"schema":{"type":"string","description":"Attachment id","title":"Attachment Id"},"description":"Attachment id"},{"name":"download","in":"query","required":false,"schema":{"type":"boolean","description":"Force a download rather than inline rendering","default":false,"title":"Download"},"description":"Force a download rather than inline rendering"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkAttachmentLink_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/messages":{"post":{"tags":["Work"],"summary":"Create Work Message","description":"Post one message into a conversation this credential may write to.\n\n``channel`` addresses the conversation — a channel name or id. Send either\n``message`` (plain text) or ``document`` (a rich-text document, normalized\nserver-side so a hostile link never reaches storage), plus optional\n``attachmentIds``, ``mentionAgentIds`` and thread parents.\n\n``403`` when the caller is not a member of the channel — an organisation\ncredential holds a seat in the built-in channels and nowhere else, so that\nis where it can post. ``404`` when no such conversation exists.\n\nMentioning an agent starts an agent turn in the background, which is how a\nmessage gets answered; the send returns as soon as the message is stored.\nThe author is resolved from the authenticated principal and the body cannot\nexpress one — ``author``, ``actor_id`` and ``org_id`` are refused outright.","operationId":"create_work_message_work_messages_post","parameters":[{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkMessageCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkMessage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/messages/{message_id}":{"get":{"tags":["Work"],"summary":"Get Work Message","description":"One message, if this credential may read the conversation carrying it.","operationId":"get_work_message_work_messages__message_id__get","parameters":[{"name":"message_id","in":"path","required":true,"schema":{"type":"string","description":"Message id","title":"Message Id"},"description":"Message id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkMessage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Work"],"summary":"Edit Work Message","description":"Correct a message this credential authored.\n\nDeliberately not a re-send: no agent turn runs again and nobody is notified,\nso an agent that already acted on the first wording is not run twice. Pass\n``expected_revision`` to make the edit conditional on the version you read.","operationId":"edit_work_message_work_messages__message_id__patch","parameters":[{"name":"message_id","in":"path","required":true,"schema":{"type":"string","description":"Message id","title":"Message Id"},"description":"Message id"},{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkMessageEditRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkMessage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Work"],"summary":"Delete Work Message","description":"Retract a message this credential authored. Soft, and safe to repeat.","operationId":"delete_work_message_work_messages__message_id__delete","parameters":[{"name":"message_id","in":"path","required":true,"schema":{"type":"string","description":"Message id","title":"Message Id"},"description":"Message id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkMessage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"work:delete","x-graph8-lifecycle":"active"}},"/work/messages/{message_id}/forward":{"post":{"tags":["Work"],"summary":"Forward Work Message","description":"Copy one message into another conversation, keeping its source attribution.\n\nBoth ends are checked: the caller must be able to read the original and to\nwrite into the destination, so forwarding can never move content into a room\nits author could not have posted in.","operationId":"forward_work_message_work_messages__message_id__forward_post","parameters":[{"name":"message_id","in":"path","required":true,"schema":{"type":"string","description":"Message id","title":"Message Id"},"description":"Message id"},{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkMessageForwardRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkMessage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/messages/{message_id}/reaction":{"put":{"tags":["Work"],"summary":"React To Work Message","description":"Add or remove one emoji reaction on a message this credential may read.\n\n``active: true`` adds it, ``false`` removes it; sending the same value twice\nis a no-op rather than an error.","operationId":"react_to_work_message_work_messages__message_id__reaction_put","parameters":[{"name":"message_id","in":"path","required":true,"schema":{"type":"string","description":"Message id","title":"Message Id"},"description":"Message id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkMessageReactionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkMessage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/activity":{"get":{"tags":["Work"],"summary":"List Work Activity","description":"What happened in Work, newest first, scoped to what this credential may read.\n\nOne row per consequential act — a message sent, a conversation created, an\napproval decided, an execution finished. Filterable by actor kind, agent,\ncategory, conversation, consequence, time window and free text.","operationId":"list_work_activity_work_activity_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","maximum":200,"minimum":1},{"type":"null"}],"description":"Page size; clamped to the server maximum","title":"Limit"},"description":"Page size; clamped to the server maximum"},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Opaque cursor from a previous page","title":"Cursor"},"description":"Opaque cursor from a previous page"},{"name":"actor","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"`human`, `agent`, `runner` or `system`","title":"Actor"},"description":"`human`, `agent`, `runner` or `system`"},{"name":"agentId","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only this agent's activity","title":"Agentid"},"description":"Only this agent's activity"},{"name":"category","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"message, conversation, approval, execution, workflow, canvas or configuration","title":"Category"},"description":"message, conversation, approval, execution, workflow, canvas or configuration"},{"name":"conversation","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only this conversation","title":"Conversation"},"description":"Only this conversation"},{"name":"consequence","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"requested, changed, approved, completed, failed or recorded","title":"Consequence"},"description":"requested, changed, approved, completed, failed or recorded"},{"name":"from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO timestamp; inclusive lower bound","title":"From"},"description":"ISO timestamp; inclusive lower bound"},{"name":"to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO timestamp; inclusive upper bound","title":"To"},"description":"ISO timestamp; inclusive upper bound"},{"name":"q","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"description":"Free text","title":"Q"},"description":"Free text"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkActivityPage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/work-items":{"get":{"tags":["Work"],"summary":"List Work Items","description":"Agent work that is RUNNING.\n\nThe in-flight half of the All Work board. An organisation credential owns no\nindividual's items, so it sees the organization's shared rows — the same\nanswer the identity filter gives any principal with no personal identity.","operationId":"list_work_items_work_work_items_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Maximum rows returned","default":50,"title":"Limit"},"description":"Maximum rows returned"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkItemList_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/work-items/history":{"get":{"tags":["Work"],"summary":"List Work Item History","description":"Agent work that has ENDED — completed, failed or cancelled, newest first.\n\nSame table and the same visibility scope as ``GET /work/work-items``; each\nrow adds ``sessionId`` when a chat session is bound to it.","operationId":"list_work_item_history_work_work_items_history_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Maximum rows returned","default":50,"title":"Limit"},"description":"Maximum rows returned"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkItemList_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/oversight":{"get":{"tags":["Work"],"summary":"Get Work Oversight","description":"What needs a person: pending approvals, blocked work and unattended fixes.\n\nRead-only, and read from the canonical approval and work-item tables rather\nthan from relay events. Each group carries its own state, so an empty list\nalways says which of \"nothing here\", \"we could not find out\" and \"nothing is\nrecorded for this workspace\" it means. Deciding an approval is not part of\nthis surface — see the module docstring.","operationId":"get_work_oversight_work_oversight_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Maximum rows PER GROUP","default":50,"title":"Limit"},"description":"Maximum rows PER GROUP"},{"name":"fix_window_hours","in":"query","required":false,"schema":{"type":"integer","maximum":720,"minimum":1,"description":"How far back autonomous fixes are read","default":24,"title":"Fix Window Hours"},"description":"How far back autonomous fixes are read"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkOversight_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/routines":{"get":{"tags":["Work"],"summary":"List Work Routines","description":"Every routine in this organization's workspace, with its recent run activity.\n\nA routine is a standing instruction to an agent, delivered into one\nconversation, on a schedule or on an event. ``503`` when the workspace has\nnever been provisioned to hold routines — nothing the caller sent is wrong.","operationId":"list_work_routines_work_routines_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkRoutineList_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"},"post":{"tags":["Work"],"summary":"Create Work Routine","description":"Create one routine.\n\n``deliveryConversationId`` must be a conversation this credential can read —\notherwise a routine would be a way to post into a room its author cannot\nsee, and it is refused with the same ``403`` reading that room would give.\n\n``triggerKind: \"schedule\"`` takes ``weekdays`` + ``localTime`` + ``timezone``;\n``triggerKind: \"event\"`` takes a ``trigger`` config and an optional\n``eventPolicy`` instead. The creator comes from the authenticated principal.","operationId":"create_work_routine_work_routines_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkRoutineCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkRoutineEnvelope_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/routines/{routine_id}":{"patch":{"tags":["Work"],"summary":"Update Work Routine","description":"Change one routine.\n\nOnly somebody who can read the routine's delivery conversation may change\nit, and re-pointing ``deliveryConversationId`` is a second grant: the NEW\nconversation must be readable too. Omitted fields keep their stored value.","operationId":"update_work_routine_work_routines__routine_id__patch","parameters":[{"name":"routine_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Routine id","title":"Routine Id"},"description":"Routine id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkRoutinePatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkRoutineEnvelope_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Work"],"summary":"Delete Work Routine","description":"Delete one routine. Same guard as changing it: the delivery conversation decides.\n\nAnswers ``200`` with the deleted id rather than the in-app ``204``: every\nDeveloper API operation returns the same ``{\"data\": ...}`` envelope, and one\nroute with no body is the exception every generated client has to special-case.","operationId":"delete_work_routine_work_routines__routine_id__delete","parameters":[{"name":"routine_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Routine id","title":"Routine Id"},"description":"Routine id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkRoutineDeleted_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"work:delete","x-graph8-lifecycle":"active"}},"/work/routines/{routine_id}/runs":{"get":{"tags":["Work"],"summary":"List Work Routine Runs","description":"The run ledger for one routine: telemetry only, newest first.\n\nA plain list. It is named in ``READ_ONLY_ACTIVE_GET_ROUTES`` so the scope\ngenerator's ``/run`` marker does not escalate reading history into\ntriggering work.","operationId":"list_work_routine_runs_work_routines__routine_id__runs_get","parameters":[{"name":"routine_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Routine id","title":"Routine Id"},"description":"Routine id"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Maximum runs returned","default":25,"title":"Limit"},"description":"Maximum runs returned"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkRoutineRunList_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"work:run","x-graph8-lifecycle":"active"}},"/work/routines/{routine_id}/run":{"post":{"tags":["Work"],"summary":"Run Work Routine Now","description":"Run one routine immediately, as the caller's own message.\n\nDeliberately not the scheduled path: the instruction is posted into the\ndelivery conversation as this credential's message and the normal turn\nmachinery answers it, so a run-now exercises exactly what a live ask would —\napprovals and all. An event routine may carry a ``sampleEvent`` to run\nagainst; it is treated as data, never as instructions.","operationId":"run_work_routine_now_work_routines__routine_id__run_post","parameters":[{"name":"routine_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Routine id","title":"Routine Id"},"description":"Routine id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/WorkRoutineRunNowRequest"},{"type":"null"}],"title":"Body"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkRoutineRunResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/projects":{"post":{"tags":["Work"],"summary":"Create Work Project","description":"Create one project in one channel.\n\n``channel`` is the channel NAME. The channel is resolved and authorized\nexactly the way a send is, so a caller who may not post in a room may not\nattach durable state to it: ``403``. The project id, the creator and the\nroom event come from the server; a body asserting them is refused by name.","operationId":"create_work_project_work_projects_post","parameters":[{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkProjectCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkProjectWriteResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/projects/{project_id}":{"patch":{"tags":["Work"],"summary":"Update Work Project","description":"Rename one project, re-describe it, or move its status.\n\n**Field PRESENCE is the contract**: an omitted field keeps its stored\nvalue and ``description: null`` clears it. ``403`` unless the caller\ncreated the project or holds Owner/Admin — the SAME rule deletion uses, and\nthe role half only answers correctly because of ``with_org_role``.","operationId":"update_work_project_work_projects__project_id__patch","parameters":[{"name":"project_id","in":"path","required":true,"schema":{"type":"string","description":"Project id","title":"Project Id"},"description":"Project id"},{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkProjectUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkProjectWriteResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Work"],"summary":"Delete Work Project","description":"Tombstone one project. Its conversation survives.\n\n``403`` unless the caller created it or holds Owner/Admin. The response\nnames what SURVIVES: the project's messages and action receipts are kept\nand counted. Repeating the call is safe. The optional body carries only an\naudit ``reason``; omitting it records ``user_requested``, as the app does.","operationId":"delete_work_project_work_projects__project_id__delete","parameters":[{"name":"project_id","in":"path","required":true,"schema":{"type":"string","description":"Project id","title":"Project Id"},"description":"Project id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/WorkProjectDeleteRequest"},{"type":"null"}],"title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkProjectDeleted_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"work:delete","x-graph8-lifecycle":"active"}},"/work/custom-emoji":{"post":{"tags":["Work"],"summary":"Add Work Custom Emoji","description":"Register one custom emoji for the whole organization.\n\n``url`` must be ``https:`` and is refused rather than coerced: a custom\nemoji renders in every member's browser. ``shortcode`` is lower-cased and\nmust be 2-32 characters of ``a-z 0-9 _ + -``. The response carries the\norganization's whole emoji set.","operationId":"add_work_custom_emoji_work_custom_emoji_post","parameters":[{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkCustomEmojiRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkCustomEmojiResult_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/pulse":{"post":{"tags":["Work"],"summary":"Add Work Pulse Note","description":"Post one pulse update — the room's org-wide, channel-less status note.\n\n``replyToEventId`` threads it under an existing note.","operationId":"add_work_pulse_note_work_pulse_post","parameters":[{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkPulseNoteRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkPulseNote_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/pulse/{note_id}/reaction":{"post":{"tags":["Work"],"summary":"Set Work Pulse Reaction","description":"Upvote one pulse note, or take the upvote back.\n\n``reacted`` is the DESIRED state, not a toggle, so a retry is idempotent.\nAlways ``200``; read ``duplicate`` to know whether anything was written.","operationId":"set_work_pulse_reaction_work_pulse__note_id__reaction_post","parameters":[{"name":"note_id","in":"path","required":true,"schema":{"type":"string","description":"Pulse note id","title":"Note Id"},"description":"Pulse note id"},{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkPulseReactionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkPulseReaction_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/signals/state":{"post":{"tags":["Work"],"summary":"Set Work Signal State","description":"Snooze or dismiss one revenue signal.\n\nNo ``Idempotency-Key``, matching the app: the key is derived from the\nsignal and the target state, so it is idempotent by construction. ``404``\nfor a signal that is not there.","operationId":"set_work_signal_state_work_signals_state_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkSignalStateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkSignalState_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/signals/promote":{"post":{"tags":["Work"],"summary":"Promote Work Signal","description":"Turn one revenue signal into an accountable Work turn in ``#work``. BILLABLE.\n\nThe promotion is an ordinary send, and like every send it schedules an\nagent turn after the write commits — which is why this is tiered\n``billable``. A replay is safe: the turn is claimed by a durable per-message\nkey, so a second call never makes a second agent answer.","operationId":"promote_work_signal_work_signals_promote_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkSignalPromoteRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkSignalPromoted_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"work:run","x-graph8-lifecycle":"active"}},"/work/team-hq/recent-activity":{"get":{"tags":["Work"],"summary":"List Work Recent Activity","description":"The Team HQ ticker's recent moments for this organization, newest first.\n\nA different feed from ``GET /work/activity`` (the room's own history): this\nis the org-wide revenue ticker, read from an org-scoped key, so another\norganization's log is unreachable by construction.","operationId":"list_work_recent_activity_work_team_hq_recent_activity_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkTickerEvents_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/team-hq/leaderboard":{"get":{"tags":["Work"],"summary":"Get Work Team Leaderboard","description":"The Team HQ board over the organization's own SDR analytics.\n\n``source`` is the honesty field: ``live``, ``cached``, ``partial`` (then\n``degradedMetrics`` names the columns that failed, ABSENT from every row\nrather than zero) or ``unavailable`` (``rows`` empty on purpose).","operationId":"get_work_team_leaderboard_work_team_hq_leaderboard_get","parameters":[{"name":"period","in":"query","required":false,"schema":{"enum":["day","month"],"type":"string","description":"`day` or `month`","default":"day","title":"Period"},"description":"`day` or `month`"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkTeamHqLeaderboard_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/team-hq/history":{"get":{"tags":["Work"],"summary":"Get Work Team History","description":"Per-rep daily series behind the board. A null day was not measured; it is not zero.","operationId":"get_work_team_history_work_team_hq_history_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","description":"Window size in days; clamped to 3-31","default":7,"title":"Days"},"description":"Window size in days; clamped to 3-31"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkTeamHqHistory_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/team-hq/receipts":{"get":{"tags":["Work"],"summary":"List Work Team Receipts","description":"One rep's recent ticker moments, newest first. ``400`` for a malformed email.","operationId":"list_work_team_receipts_work_team_hq_receipts_get","parameters":[{"name":"email","in":"query","required":true,"schema":{"type":"string","description":"The rep whose recent moments to list","title":"Email"},"description":"The rep whose recent moments to list"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","description":"Max events; clamped to 1-50","default":20,"title":"Limit"},"description":"Max events; clamped to 1-50"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkTickerEvents_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/read-markers":{"get":{"tags":["Work"],"summary":"Get Work Read Markers","description":"How far THIS principal has read each conversation. Never anybody else's.","operationId":"get_work_read_markers_work_read_markers_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkReadMarkers_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"},"post":{"tags":["Work"],"summary":"Set Work Read Markers","description":"Record that this principal has read these conversations up to a point.\n\nBatched (1-200 markers per request) and monotonic: a marker that moves\nbackwards is ignored, so a replay changes nothing and no key is asked for.","operationId":"set_work_read_markers_work_read_markers_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkReadMarkersRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkReadMarkers_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/inbox-dispositions":{"get":{"tags":["Work"],"summary":"Get Work Inbox Dispositions","description":"THIS principal's Inbox states, keyed by conversation. Never anybody else's.","operationId":"get_work_inbox_dispositions_work_inbox_dispositions_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkInboxDispositions_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"},"post":{"tags":["Work"],"summary":"Set Work Inbox Disposition","description":"Snooze, archive or reactivate one conversation, for this principal only.\n\n``state: \"snoozed\"`` REQUIRES a future ``snoozedUntil``; the app refuses a\nsnooze without a wake-up with a 422.","operationId":"set_work_inbox_disposition_work_inbox_dispositions_post","parameters":[{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again — send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkInboxDispositionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkInboxDisposition_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/sidebar-preferences":{"post":{"tags":["Work"],"summary":"Set Work Sidebar Preferences","description":"Store how this principal wants its own sidebar ordered.\n\nBoth halves are required and closed to ``alpha`` | ``recent``. There is no\nread route here because there is none in the app: the stored value rides\nthe room payload (``GET /work/room``).","operationId":"set_work_sidebar_preferences_work_sidebar_preferences_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkSidebarPreferencesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkSidebarPreferences_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/preferences/daily-brief":{"get":{"tags":["Work"],"summary":"Get Work Daily Brief","description":"THIS principal's daily-brief schedule, plus when the next one is due and why.","operationId":"get_work_daily_brief_work_preferences_daily_brief_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkDailyBriefSettings_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"},"post":{"tags":["Work"],"summary":"Set Work Daily Brief","description":"Store THIS principal's daily-brief schedule.\n\nAn unknown ``timezone`` is a 422 rather than a UTC guess: a brief is a\nscheduled send, and a wrong zone delivers a morning brief at midnight.","operationId":"set_work_daily_brief_work_preferences_daily_brief_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkDailyBriefSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkDailyBriefSettings_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/document-templates":{"get":{"tags":["Work"],"summary":"List Work Document Templates","description":"The templates a channel document can start from: `templates[]` with `id`, `title` and `description`.","operationId":"list_work_document_templates_work_document_templates_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/channels/{channel_id}/outputs":{"get":{"tags":["Work"],"summary":"List Work Channel Outputs","description":"The channel's output links, documents first, newest first: `outputs[]` and `canEdit`.\n\n`canEdit` is the caller's canvas-write authority: whether creating, renaming and removing outputs will be allowed.\n403 (one body) for an unknown conversation or a channel the caller has no seat in. A shared (cross-org) channel\nanswers an empty list.","operationId":"list_work_channel_outputs_work_channels__channel_id__outputs_get","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Channel id or slug","title":"Channel Id"},"description":"Channel id or slug"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/channels/{channel_id}/outputs/{output_id}/document":{"get":{"tags":["Work"],"summary":"Get Work Channel Output Document","description":"A linked document's body: `id`, `display_name`, `content` (Markdown), `updated_at` and `canEdit`. 404 for an unknown output.","operationId":"get_work_channel_output_document_work_channels__channel_id__outputs__output_id__document_get","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Channel id or slug","title":"Channel Id"},"description":"Channel id or slug"},{"name":"output_id","in":"path","required":true,"schema":{"type":"string","description":"Output id","title":"Output Id"},"description":"Output id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"},"put":{"tags":["Work"],"summary":"Put Work Channel Output Document","description":"Replace a linked document's body (Markdown, whole). Needs canvas-write authority in the channel.\n\n`expectedUpdatedAt` makes the save conditional: 409 if the document changed since you read it.","operationId":"put_work_channel_output_document_work_channels__channel_id__outputs__output_id__document_put","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Channel id or slug","title":"Channel Id"},"description":"Channel id or slug"},{"name":"output_id","in":"path","required":true,"schema":{"type":"string","description":"Output id","title":"Output Id"},"description":"Output id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkDocumentBodyBody"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/channels/{channel_id}/outputs/documents":{"post":{"tags":["Work"],"summary":"Create Work Channel Document","description":"Create a document from a template and link it: `output` and `duplicate`.\n\n403 for an archived or shared channel or no canvas-write authority, 422 for an unknown template or a bad title, 409\nwhen the channel is full.","operationId":"create_work_channel_document_work_channels__channel_id__outputs_documents_post","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Channel id or slug","title":"Channel Id"},"description":"Channel id or slug"},{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again: send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again: send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkDocumentCreateBody"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/channels/{channel_id}/outputs/{output_id}":{"patch":{"tags":["Work"],"summary":"Rename Work Channel Output","description":"Rename an output (and its document): `output` and `duplicate`. 404 for an unknown output.","operationId":"rename_work_channel_output_work_channels__channel_id__outputs__output_id__patch","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Channel id or slug","title":"Channel Id"},"description":"Channel id or slug"},{"name":"output_id","in":"path","required":true,"schema":{"type":"string","description":"Output id","title":"Output Id"},"description":"Output id"},{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again: send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again: send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkOutputRenameBody"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Work"],"summary":"Remove Work Channel Output","description":"Unlink an output: `removed` and `duplicate`. The document is tombstoned (hidden, unreachable, later purged).","operationId":"remove_work_channel_output_work_channels__channel_id__outputs__output_id__delete","parameters":[{"name":"channel_id","in":"path","required":true,"schema":{"type":"string","description":"Channel id or slug","title":"Channel Id"},"description":"Channel id or slug"},{"name":"output_id","in":"path","required":true,"schema":{"type":"string","description":"Output id","title":"Output Id"},"description":"Output id"},{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again: send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again: send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"work:delete","x-graph8-lifecycle":"active"}},"/work/conversations/{conversation_key}/activity":{"get":{"tags":["Work"],"summary":"Get Work Conversation Activity","description":"What the agent in this conversation is doing: open items, or recent ones with summary and read state.\n\nThe same access predicate the room read uses: an unknown and an unreadable conversation are the same 403.","operationId":"get_work_conversation_activity_work_conversations__conversation_key__activity_get","parameters":[{"name":"conversation_key","in":"path","required":true,"schema":{"type":"string","description":"Conversation id (or channel key)","title":"Conversation Key"},"description":"Conversation id (or channel key)"},{"name":"state","in":"query","required":false,"schema":{"enum":["open","recent"],"type":"string","description":"`open` (running or waiting on you) or `recent` (finished this week).","default":"open","title":"State"},"description":"`open` (running or waiting on you) or `recent` (finished this week)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/conversations/{conversation_id}/decisions":{"get":{"tags":["Work"],"summary":"Get Work Conversation Decisions","description":"The latest decision posts of ONE conversation, and the pinned status post. Membership-gated; read-only.","operationId":"get_work_conversation_decisions_work_conversations__conversation_id__decisions_get","parameters":[{"name":"conversation_id","in":"path","required":true,"schema":{"type":"string","description":"Conversation id (or channel key)","title":"Conversation Id"},"description":"Conversation id (or channel key)"},{"name":"limit","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Decisions to return; clamped to the server cap.","title":"Limit"},"description":"Decisions to return; clamped to the server cap."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/conversations/{conversation_id}/tasks":{"get":{"tags":["Work"],"summary":"List Work Conversation Tasks","description":"The channel's tasks: `waitingOnYou`, `running`, `done` (agent work) and `people` (tasks people were given here).\n\nYour own task scope decides which people-tasks you see. 403 for a conversation you cannot read, an unknown one, and\nan organisation key (a task belongs to a person).","operationId":"list_work_conversation_tasks_work_conversations__conversation_id__tasks_get","parameters":[{"name":"conversation_id","in":"path","required":true,"schema":{"type":"string","description":"Conversation id (or channel key)","title":"Conversation Id"},"description":"Conversation id (or channel key)"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Max tasks per group, and in `people`.","default":20,"title":"Limit"},"description":"Max tasks per group, and in `people`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"},"post":{"tags":["Work"],"summary":"Create Work Conversation Task","description":"Give a task to a person from this channel: a task on the CRM task board, not an agent run.\n\nThe creator, organisation and channel come from the key and the URL, never the body. `ownerUserId` names the\nASSIGNEE (the caller when omitted), who must be the caller or a human member of the conversation. Needs a seat in the\nchannel; a person may start at most 30 new tasks per 10 minutes (429). A replayed `Idempotency-Key` returns the\noriginal task with `duplicate: true`; the same key with a different body is a 409.","operationId":"create_work_conversation_task_work_conversations__conversation_id__tasks_post","parameters":[{"name":"conversation_id","in":"path","required":true,"schema":{"type":"string","description":"Conversation id (or channel key)","title":"Conversation Id"},"description":"Conversation id (or channel key)"},{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again: send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again: send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkChannelTaskCreateBody"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/conversations/{conversation_key}/turns/{turn_id}/cancel":{"post":{"tags":["Work"],"summary":"Cancel Work Turn","description":"Ask the agent turn answering `turn_id` to stop. Cooperative and idempotent: it finishes its current step.\n\nAllowed for the person who sent the turn's message and for an Owner or Admin. `status` is `stopping`, or\n`unavailable` (503) when nothing recorded the stop and nothing is running. 409 for a shared channel's turn.","operationId":"cancel_work_turn_work_conversations__conversation_key__turns__turn_id__cancel_post","parameters":[{"name":"conversation_key","in":"path","required":true,"schema":{"type":"string","description":"Conversation id (or channel key)","title":"Conversation Key"},"description":"Conversation id (or channel key)"},{"name":"turn_id","in":"path","required":true,"schema":{"type":"string","description":"The id of the message the turn is answering.","title":"Turn Id"},"description":"The id of the message the turn is answering."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"work:delete","x-graph8-lifecycle":"active"}},"/work/chats":{"post":{"tags":["Work"],"summary":"Create Work Chat","description":"Open a new chat with the caller's Chief of Staff and the operator bench. PERSONAL KEY ONLY.\n\n`201` with `directMessage` (a chat IS a direct-message conversation; its payload carries `workChat`) and `duplicate`.\nWith `initialMessage` the first message is posted in the same request and the Chief's turn STARTS, which SPENDS\ncredits; the body then also carries `message`. A replayed `Idempotency-Key` returns the same chat; a new key opens a\nnew one. 503 while chats are switched off.","operationId":"create_work_chat_work_chats_post","parameters":[{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again: send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again: send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkChatCreateBody"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"work:run","x-graph8-lifecycle":"active"}},"/work/chats/{chat_id}/channel-name":{"get":{"tags":["Work"],"summary":"Suggest Work Chat Channel Name","description":"A suggested channel name for converting this chat: `name`, or `null` when naming is off or fails. PERSONAL KEY ONLY.\n\nOne fast-tier model call; writes nothing. 404 or 409 from the convert's own chat check.","operationId":"suggest_work_chat_channel_name_work_chats__chat_id__channel_name_get","parameters":[{"name":"chat_id","in":"path","required":true,"schema":{"type":"string","description":"Chat id","title":"Chat Id"},"description":"Chat id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/chats/{chat_id}/convert":{"post":{"tags":["Work"],"summary":"Convert Work Chat","description":"Turn a chat into a private channel named `name`, history intact. PERSONAL KEY ONLY.\n\n`201` with `channel`, `chatId`, `agentIds`, `copiedMessages` and `duplicate`. 404 for a chat that is not the caller's,\n409 when the name is taken or the chat was already converted, 422 for a name that cannot be a channel name.","operationId":"convert_work_chat_work_chats__chat_id__convert_post","parameters":[{"name":"chat_id","in":"path","required":true,"schema":{"type":"string","description":"Chat id","title":"Chat Id"},"description":"Chat id"},{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again: send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again: send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkChatConvertBody"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/chats/{chat_id}":{"patch":{"tags":["Work"],"summary":"Update Work Chat","description":"Rename a chat and/or archive or restore it for the caller. PERSONAL KEY ONLY.\n\nArchive is per person; rename is for everyone. Send `title`, `archived`, or both. 404 for a chat that is not the\ncaller's, 409 once it became a channel, 422 for an empty name.","operationId":"update_work_chat_work_chats__chat_id__patch","parameters":[{"name":"chat_id","in":"path","required":true,"schema":{"type":"string","description":"Chat id","title":"Chat Id"},"description":"Chat id"},{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again: send your own for anything you may retry.","title":"Idempotency-Key"},"description":"Retry-safety key. Replaying one returns the ORIGINAL result with `duplicate: true` instead of writing twice. Omit it and the server mints a single-use key, which means a retried request writes again: send your own for anything you may retry."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkChatUpdateBody"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkChannelPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/agents/policy":{"get":{"tags":["Work"],"summary":"Get Work Agent Policy","description":"What this caller may do with Work agents: create a private one, share one org-wide.","operationId":"get_work_agent_policy_work_agents_policy_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkAgentPolicy_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/agents/execution-identities":{"get":{"tags":["Work"],"summary":"List Work Agent Execution Identities","description":"The agent identities this caller may run work as.\n\nA source that could not be read degrades to a ``warnings`` entry rather than\nfailing the list, as in the app.","operationId":"list_work_agent_execution_identities_work_agents_execution_identities_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkAgentExecutionIdentities_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"}},"/work/agents":{"get":{"tags":["Work"],"summary":"List Work Agents","description":"The Work agents this caller may see: their own and the organization's shared ones.","operationId":"list_work_agents_work_agents_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Page size","default":50,"title":"Limit"},"description":"Page size"},{"name":"after","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"description":"`next_cursor` from the previous page","title":"After"},"description":"`next_cursor` from the previous page"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkAgentProfilePage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"},"post":{"tags":["Work"],"summary":"Create Work Agent","description":"Create one Work agent and its conversation.\n\n``visibility: \"organization\"`` needs the share permission (see\n``GET /work/agents/policy``); ``403`` otherwise. Creating does not run it.","operationId":"create_work_agent_work_agents_post","parameters":[{"name":"Idempotency-Key","in":"header","required":false,"schema":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"description":"Retry-safety key (a UUID). Replaying one returns the ORIGINAL agent instead of creating a second. Omit it and the server mints one, so a retried request creates again.","title":"Idempotency-Key"},"description":"Retry-safety key (a UUID). Replaying one returns the ORIGINAL agent instead of creating a second. Omit it and the server mints one, so a retried request creates again."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkAgentProfileRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkAgentCreated_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/agents/{agent_id}":{"get":{"tags":["Work"],"summary":"Get Work Agent","description":"One Work agent. ``403`` when it is another person's private agent.","operationId":"get_work_agent_work_agents__agent_id__get","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Agent id","title":"Agent Id"},"description":"Agent id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkAgentProfile_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Work"],"summary":"Update Work Agent","description":"Replace one agent's profile, versioned.\n\n``expected_version`` is the ``version`` you read; a stale one is a ``409``\nso two editors cannot silently overwrite each other's instructions.","operationId":"update_work_agent_work_agents__agent_id__patch","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Agent id","title":"Agent Id"},"description":"Agent id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkAgentProfileEditRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkAgentProfile_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Work"],"summary":"Archive Work Agent","description":"Archive one Work agent. ``403`` unless the caller may edit it.\n\nThe app answers ``204``; this answers ``200`` with the archived id so the\nresponse fits the Developer API envelope.","operationId":"archive_work_agent_work_agents__agent_id__delete","parameters":[{"name":"agent_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Agent id","title":"Agent Id"},"description":"Agent id"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkAgentArchived_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"work:delete","x-graph8-lifecycle":"active"}},"/work/memory":{"get":{"tags":["Work"],"summary":"Get Work Memory","description":"Every topic in one memory scope, and whether this caller may edit it.","operationId":"get_work_memory_work_memory_get","parameters":[{"name":"scope","in":"query","required":false,"schema":{"enum":["personal","agent","team"],"type":"string","description":"`personal`, `agent` or `team`","default":"personal","title":"Scope"},"description":"`personal`, `agent` or `team`"},{"name":"agent_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"description":"Required for, and only for, `agent` scope","title":"Agent Id"},"description":"Required for, and only for, `agent` scope"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkMemoryPage_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"work:read","x-graph8-lifecycle":"active"},"put":{"tags":["Work"],"summary":"Edit Work Memory","description":"Replace one memory topic. ``expected_revision`` is a compare-and-swap; stale is ``409``.","operationId":"edit_work_memory_work_memory_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkMemoryEditRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkMemoryNote_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/work/memory/move":{"post":{"tags":["Work"],"summary":"Move Work Memory","description":"Move one topic between scopes, guarded by both sides' revisions.","operationId":"move_work_memory_work_memory_move_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkMemoryMoveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkMemoryNote_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"work:write","x-graph8-lifecycle":"active"}},"/marketplace/me/profile":{"get":{"tags":["Marketplace"],"summary":"Get the caller's marketplace SDR profile","description":"Return the caller's own marketplace SDR profile + ``is_complete`` flag.\n\nRequires a *personal* API key. Org-scoped keys 404.","operationId":"get_my_marketplace_profile_marketplace_me_profile_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceProfileResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Marketplace"],"summary":"Update My Marketplace Profile","description":"Edit your own marketplace profile. Partial - omitted fields are untouched.\n\nRead `completeness.blocking_reasons` in the response rather than guessing:\nit names exactly what is still keeping the profile off the browse list,\nwhich is a different question from `is_complete` (the form is filled in) and\nfrom `is_visible_eligible` (you are actually live to buyers).\n\nCHANGING `country_code` RECOMPUTES YOUR PAYOUT RAIL and cascades to the\nconnect and payout-account rows; an unsupported country is refused with a\n400 rather than landing you on a rail that cannot pay you. An agency-managed\nrep cannot edit their rates here (403) - the agency sets the client price.\n\nSending an empty body is a no-op that returns the current profile, matching\nthe app.","operationId":"update_my_marketplace_profile_marketplace_me_profile_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TalentProfileUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/offers":{"get":{"tags":["Marketplace"],"summary":"List the caller's pending marketplace hire offers","description":"List pending hire offers sent to the caller's SDR profile, enriched\nwith the hiring org's display name. Requires a personal API key.","operationId":"list_my_marketplace_offers_marketplace_me_offers_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceOffersResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/me/offers/{hiring_id}/accept":{"post":{"tags":["Marketplace"],"summary":"Accept a pending marketplace hire offer (SDR side)","description":"Accept a pending hire offer.\n\nDelegates to ``marketplace.self_service_router.accept_offer`` so the\nfull side-effect chain runs intact: hiring transitions to ``active``,\nthe hiring-fee invoice is created, the SDR gains PropelAuth membership\nin the client org (Member role; ``service_provider`` for commission-only\nhires), the client gets a notification, and the EDA event fires.\n\nRequires a personal API key — the underlying handler scopes ownership\nvia the SDR profile resolved from the caller's email.","operationId":"accept_my_offer_marketplace_me_offers__hiring_id__accept_post","parameters":[{"name":"hiring_id","in":"path","required":true,"schema":{"type":"string","title":"Hiring Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/offers/{hiring_id}/reject":{"post":{"tags":["Marketplace"],"summary":"Reject a pending marketplace hire offer (SDR side)","description":"Reject a pending hire offer. Notifies the client and flips the\nhiring row to ``rejected``.","operationId":"reject_my_offer_marketplace_me_offers__hiring_id__reject_post","parameters":[{"name":"hiring_id","in":"path","required":true,"schema":{"type":"string","title":"Hiring Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/hirings":{"get":{"tags":["Marketplace"],"summary":"List the caller's active marketplace hirings","description":"List active hiring contracts where the caller is the SDR side.","operationId":"list_my_marketplace_hirings_marketplace_me_hirings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceHiringsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/me/meetings":{"get":{"tags":["Marketplace"],"summary":"List the caller's meetings across all hirings","description":"List the caller's meetings across all hirings. Personal API key only.","operationId":"list_my_meetings_marketplace_me_meetings_get","parameters":[{"name":"hiring_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Optional: restrict to one hiring","title":"Hiring Id"},"description":"Optional: restrict to one hiring"},{"name":"meeting_status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"scheduled | taken | rescheduled | missed | cancelled","title":"Meeting Status"},"description":"scheduled | taken | rescheduled | missed | cancelled"},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"YYYY-MM-DD inclusive","title":"Start Date"},"description":"YYYY-MM-DD inclusive"},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"YYYY-MM-DD inclusive","title":"End Date"},"description":"YYYY-MM-DD inclusive"},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Match contact name / email / notes","title":"Search"},"description":"Match contact name / email / notes"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceMeetingsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/me/meetings/{meeting_id}":{"get":{"tags":["Marketplace"],"summary":"Get a single meeting (SDR side)","operationId":"get_my_meeting_marketplace_me_meetings__meeting_id__get","parameters":[{"name":"meeting_id","in":"path","required":true,"schema":{"type":"string","title":"Meeting Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceMeetingDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Marketplace"],"summary":"Update meeting notes + contact info (SDR side)","description":"Employee-side meeting edit — notes + contact info only.\n\nLifecycle fields (status, meeting_date, meeting_type, hiring_id) are\nintentionally NOT editable here. Those are client-owned via the\ncalendar-driven sync.","operationId":"update_my_meeting_marketplace_me_meetings__meeting_id__patch","parameters":[{"name":"meeting_id","in":"path","required":true,"schema":{"type":"string","title":"Meeting Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateMyMeetingRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceMeetingDetail_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/invoices":{"get":{"tags":["Marketplace"],"summary":"List the caller's marketplace invoices","operationId":"list_my_marketplace_invoices_marketplace_me_invoices_get","parameters":[{"name":"invoice_status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Invoice Status"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceInvoicesResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"},"post":{"tags":["Marketplace"],"summary":"Submit a monthly invoice for a hiring contract","description":"Submit a monthly invoice. Computes meeting count + amounts via the\nexisting ``CreateSdrInvoiceHandler``, transitions to ``pending``, and\nstarts the client's 5-calendar-day review window.","operationId":"submit_my_invoice_marketplace_me_invoices_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SubmitInvoiceRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/invoices/{invoice_id}/approve":{"post":{"tags":["Marketplace"],"summary":"SDR approves their own draft invoice (sdr_review → pending)","description":"SDR-side approve. Transitions ``sdr_review`` → ``pending``, sets\n``submitted_at`` and a 5-day ``due_date``. After due_date the\nauto-charge task fires on the client. Different surface from\n``/marketplace/org/invoices/{id}/approve`` (which the client uses\nto release payment immediately).","operationId":"approve_my_invoice_marketplace_me_invoices__invoice_id__approve_post","parameters":[{"name":"invoice_id","in":"path","required":true,"schema":{"type":"string","title":"Invoice Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/connect/status":{"get":{"tags":["Marketplace"],"summary":"Get the caller's Stripe Connect onboarding status","description":"Returns the caller's Stripe Connect account state, enriched with\nlive Stripe data and self-healing for missed webhooks.","operationId":"get_my_connect_status_marketplace_me_connect_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceConnectStatusResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/me/payout-account":{"get":{"tags":["Marketplace"],"summary":"Get the caller's payout account status","description":"Get the caller's payout account (Stripe Connect / Wise / fallback).","operationId":"get_my_payout_account_marketplace_me_payout_account_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayoutAccountResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/org/invoices":{"get":{"tags":["Marketplace"],"summary":"List SDR invoices owed by the caller's org","description":"List invoices sent to the caller's org by marketplace SDRs.","operationId":"list_org_marketplace_invoices_marketplace_org_invoices_get","parameters":[{"name":"invoice_status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Invoice Status"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceInvoicesResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/org/invoices/{invoice_id}":{"get":{"tags":["Marketplace"],"summary":"Get one SDR invoice (org side)","description":"Get full detail for one invoice owed by the caller's org. Includes\nSDR profile + hiring contract context, so an agent can render the\nfull \"approve or dispute\" UI from a single call.","operationId":"get_org_invoice_marketplace_org_invoices__invoice_id__get","parameters":[{"name":"invoice_id","in":"path","required":true,"schema":{"type":"string","title":"Invoice Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/org/invoices/{invoice_id}/approve":{"post":{"tags":["Marketplace"],"summary":"Approve an SDR invoice → triggers immediate Stripe charge","description":"Approve an SDR invoice and trigger immediate charge via Stripe.\n\nDelegates to ``marketplace.org_invoice_router.approve_invoice`` so the\n``ChargeInvoiceHandler`` runs intact: status flips to ``charged``,\nStripe processes the transfer to the SDR's Connect account, and the\nSDR gets a \"your invoice was approved\" notification.\n\nAuth: requires a personal API key whose user has the Admin or Owner\nrole in the calling org (``require_org_admin``). Org-scoped (machine)\nkeys are refused — see ``developer_api.dependencies.admin``. The\nrationale: this call fires an immediate Stripe charge on the org's\ndefault payment method. Letting a non-admin or a machine key trigger\nthat would be a meaningful surface for unintended debits.","operationId":"approve_org_invoice_marketplace_org_invoices__invoice_id__approve_post","parameters":[{"name":"invoice_id","in":"path","required":true,"schema":{"type":"string","title":"Invoice Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/org/invoices/{invoice_id}/dispute":{"post":{"tags":["Marketplace"],"summary":"Dispute an SDR invoice within the grace period","description":"Dispute an SDR invoice. Must be in ``pending`` state and within the\ngrace period (the 5-calendar-day review window after submission).\n\nAuth: requires a personal API key whose user has the Admin or Owner\nrole in the calling org (``require_org_admin``). MBM PR #8575\nround-7 review flagged that ``dispute_org_invoice`` is marked\n``_DESTRUCTIVE`` at the MCP layer (\"decide deliberately\") but had\nno developer_api gate. We gate it here for the same reason it's\nDESTRUCTIVE in MCP: opening a dispute notifies the SDR, escalates to\nops for resolution, damages the engagement, and there is no\nun-dispute API. Sibling consistency with ``approve_org_invoice`` and\n``terminate_org_hiring`` — every destructive ``/org/*`` route\nrequires the same role.","operationId":"dispute_org_invoice_marketplace_org_invoices__invoice_id__dispute_post","parameters":[{"name":"invoice_id","in":"path","required":true,"schema":{"type":"string","title":"Invoice Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DisputeInvoiceRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/org/hirings":{"get":{"tags":["Marketplace"],"summary":"List active SDR hirings for the caller's org","description":"List active hiring contracts where the caller's org is the client.","operationId":"list_org_marketplace_hirings_marketplace_org_hirings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceHiringsResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/org/hirings/{hiring_id}":{"get":{"tags":["Marketplace"],"summary":"Get one hiring contract (org side)","description":"Get one hiring contract for the caller's org, enriched with SDR\nprofile metadata.","operationId":"get_org_hiring_marketplace_org_hirings__hiring_id__get","parameters":[{"name":"hiring_id","in":"path","required":true,"schema":{"type":"string","title":"Hiring Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/org/hirings/{hiring_id}/terminate":{"post":{"tags":["Marketplace"],"summary":"Terminate an active hiring contract (org side)","description":"Terminate an active hiring. The SDR still receives a final\nprorated invoice at the next monthly billing run covering work\nthrough the termination date.\n\nAuth: requires a personal API key whose user has the Admin or Owner\nrole in the calling org (``require_org_admin``). Org-scoped (machine)\nkeys are refused — see ``developer_api.dependencies.admin``. The\nrationale: termination ends a paid commercial relationship and is not\nreversible from this surface (the client must send a fresh hire offer\nto re-engage). Restricting the trigger to org admins matches the\norg's intent that contract lifecycle is a leadership-level decision.","operationId":"terminate_org_hiring_marketplace_org_hirings__hiring_id__terminate_post","parameters":[{"name":"hiring_id","in":"path","required":true,"schema":{"type":"string","title":"Hiring Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/org/hirings/{hiring_id}/withdraw":{"post":{"tags":["Marketplace"],"summary":"Withdraw a pending hiring offer (org side)","description":"Withdraw an offer the talent has not yet accepted (``pending_acceptance``).\n\nThe recovery path for an offer sent to the wrong talent or with wrong\nterms. Voids the contract envelope so it can no longer be signed. No\ninvoice is generated — an unsigned offer never created a billable\nrelationship. Returns 409 if the offer is already active (terminate it\ninstead) or already terminated.\n\nAuth mirrors terminate: a personal API key with Admin/Owner role in the\ncalling org (``require_org_admin``); org-scoped machine keys are refused.\nContract lifecycle stays a leadership-level decision.","operationId":"withdraw_org_hiring_marketplace_org_hirings__hiring_id__withdraw_post","parameters":[{"name":"hiring_id","in":"path","required":true,"schema":{"type":"string","title":"Hiring Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/talent":{"get":{"tags":["Marketplace"],"summary":"Browse available SDR/AE/GTM marketplace profiles","description":"Browse marketplace talent.\n\nReturns visible (complete + active) profiles, with the caller's\nalready-hired SDRs filtered out. Anonymous profiles are masked unless\nthe caller's org has previously hired them. Optional ``match_score``\nis merged in from the per-org talent-match cache.","operationId":"browse_talent_marketplace_talent_get","parameters":[{"name":"country_code","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country Code"}},{"name":"payout_track","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Payout Track"}},{"name":"role","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"sdr | ae | gtm_engineer","title":"Role"},"description":"sdr | ae | gtm_engineer"},{"name":"availability","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"open | limited | fully_booked","title":"Availability"},"description":"open | limited | fully_booked"},{"name":"tier","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Certification tier (TitleCase, case-sensitive). AE tiers: 'Top Performer' | 'Leadership-track' | 'Senior' | 'Solid' | 'Transition'. SDR tiers: 'Strategic' | 'Data-Driven' | 'Independent' | 'Disciplined'. Canonical list lives in marketplace/usecases/admin_analytics/_shared.py::KNOWN_TIERS. Any other value silently returns an empty result set — that's the underlying DB filter behaviour, not a bug here.","title":"Tier"},"description":"Certification tier (TitleCase, case-sensitive). AE tiers: 'Top Performer' | 'Leadership-track' | 'Senior' | 'Solid' | 'Transition'. SDR tiers: 'Strategic' | 'Data-Driven' | 'Independent' | 'Disciplined'. Canonical list lives in marketplace/usecases/admin_analytics/_shared.py::KNOWN_TIERS. Any other value silently returns an empty result set — that's the underlying DB filter behaviour, not a bug here."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":5000,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/talent/{sdr_id}":{"get":{"tags":["Marketplace"],"summary":"Get one talent profile (masked unless already hired)","description":"Get one talent profile. Anonymous profiles stay masked unless the\ncaller's org has previously hired this SDR (permanent reveal). Emits\na ``profile_view`` funnel event.","operationId":"get_talent_profile_marketplace_talent__sdr_id__get","parameters":[{"name":"sdr_id","in":"path","required":true,"schema":{"type":"string","title":"Sdr Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/talent/{sdr_id}/match":{"get":{"tags":["Marketplace"],"summary":"Get the cached talent-org match score","description":"Get the cached match score for this org × this talent.\n\nIf no score exists yet, dispatches an async compute and returns\n``{\"status\": \"generating\"}`` with a ``202 Accepted``. Subsequent calls\nreturn the computed score (200) once the worker lands.","operationId":"get_talent_match_marketplace_talent__sdr_id__match_get","parameters":[{"name":"sdr_id","in":"path","required":true,"schema":{"type":"string","title":"Sdr Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/talent/{sdr_id}/hire":{"post":{"tags":["Marketplace"],"summary":"Send a hire offer to a talent profile","description":"Send a hire offer.\n\nDelegates to ``HireSdrHandler`` so the full chain runs intact:\nSdrHiring row is created in ``pending_acceptance`` state, the contract\nis generated + e-signed inside graph8, the client's T&C acceptance is\nstamped in the same transaction, the SDR receives a \"you have a new\noffer\" notification, and the EDA event fires.\n\n409 if the caller already has an active contract with this SDR.\n400 if ``accepted_terms`` is empty (terms_not_accepted).","operationId":"hire_talent_marketplace_talent__sdr_id__hire_post","parameters":[{"name":"sdr_id","in":"path","required":true,"schema":{"type":"string","title":"Sdr Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/HireSdrRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/admin/analytics/funnel":{"get":{"tags":["Marketplace"],"summary":"Section A — SDR supply funnel (platform admin only)","description":"SDR supply-side conversion funnel for the given window.","operationId":"admin_funnel_marketplace_admin_analytics_funnel_get","parameters":[{"name":"from","in":"query","required":true,"schema":{"type":"string","description":"YYYY-MM-DD","title":"From"},"description":"YYYY-MM-DD"},{"name":"to","in":"query","required":true,"schema":{"type":"string","description":"YYYY-MM-DD","title":"To"},"description":"YYYY-MM-DD"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/admin/analytics/hires":{"get":{"tags":["Marketplace"],"summary":"Section C — hire conversion, termination, rehire metrics","operationId":"admin_hires_marketplace_admin_analytics_hires_get","parameters":[{"name":"from","in":"query","required":true,"schema":{"type":"string","description":"YYYY-MM-DD","title":"From"},"description":"YYYY-MM-DD"},{"name":"to","in":"query","required":true,"schema":{"type":"string","description":"YYYY-MM-DD","title":"To"},"description":"YYYY-MM-DD"},{"name":"group_by","in":"query","required":false,"schema":{"type":"string","description":"day | week | month","default":"month","title":"Group By"},"description":"day | week | month"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/admin/analytics/revenue":{"get":{"tags":["Marketplace"],"summary":"Section D — GMV, net commission, money-loop distribution","operationId":"admin_revenue_marketplace_admin_analytics_revenue_get","parameters":[{"name":"from","in":"query","required":true,"schema":{"type":"string","description":"YYYY-MM-DD","title":"From"},"description":"YYYY-MM-DD"},{"name":"to","in":"query","required":true,"schema":{"type":"string","description":"YYYY-MM-DD","title":"To"},"description":"YYYY-MM-DD"},{"name":"group_by","in":"query","required":false,"schema":{"type":"string","description":"day | week | month","default":"month","title":"Group By"},"description":"day | week | month"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/admin/analytics/operational":{"get":{"tags":["Marketplace"],"summary":"Section F — operational health (SLAs, disputes, payouts)","operationId":"admin_operational_marketplace_admin_analytics_operational_get","parameters":[{"name":"from","in":"query","required":true,"schema":{"type":"string","description":"YYYY-MM-DD","title":"From"},"description":"YYYY-MM-DD"},{"name":"to","in":"query","required":true,"schema":{"type":"string","description":"YYYY-MM-DD","title":"To"},"description":"YYYY-MM-DD"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/job-posts":{"post":{"tags":["Marketplace"],"summary":"Create a marketplace job post (Open Role)","description":"Create an Open Role under the calling key's org. The role's title,\ndescription (the client's JD), criteria, comp, and openings live in the\nbody. Send ``status=\"published\"`` to go live to talent immediately, or\n``\"draft\"`` (default) to stage it and publish later via PATCH.","operationId":"create_marketplace_job_post_marketplace_job_posts_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/JobPostCreate"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"},"get":{"tags":["Marketplace"],"summary":"List the calling org's job posts","description":"List every role this org has posted (any status), newest first.","operationId":"list_marketplace_job_posts_marketplace_job_posts_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/job-posts/{post_id}":{"get":{"tags":["Marketplace"],"summary":"Get one job post the org owns","operationId":"get_marketplace_job_post_marketplace_job_posts__post_id__get","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Post Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Marketplace"],"summary":"Edit a job post or change its status (publish/pause/close/filled)","description":"Partial update. Any subset of the role fields may be sent; only provided\nfields change. Set ``status`` to move the role through\ndraft → published → paused → closed | filled.","operationId":"update_marketplace_job_post_marketplace_job_posts__post_id__patch","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Post Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/JobPostUpdate"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Marketplace"],"summary":"Delete a job post the org owns","description":"Hard-delete a role plus its applications and role-match scores. Use for\ndraft/test or obsolete roles.\n\nGuarded: if the role has applications, this 409s unless ``force=true`` — so\nan automated caller can't wipe an applicant inbox by mistake. Pass\n``?force=true`` to confirm deletion of a role that already has applicants.","operationId":"delete_marketplace_job_post_marketplace_job_posts__post_id__delete","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Post Id"}},{"name":"force","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Force"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"marketplace:delete","x-graph8-lifecycle":"active"}},"/marketplace/job-posts/{post_id}/applications":{"get":{"tags":["Marketplace"],"summary":"List applicants for a job post (applicant inbox)","description":"Applicant inbox for a role — each applicant with their role-scoped\nmatch scorecard and status (viewed / shortlisted / rejected / offer_sent /\nhired). This is how graph8 tracks everyone who applied.","operationId":"list_marketplace_job_post_applications_marketplace_job_posts__post_id__applications_get","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Post Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/applications/{application_id}":{"patch":{"tags":["Marketplace"],"summary":"Update an applicant (shortlist / reject / link a hiring)","description":"Move an applicant through the review pipeline (status = viewed /\nshortlisted / rejected / offer_sent / hired) or link a created hiring.","operationId":"patch_marketplace_application_marketplace_applications__application_id__patch","parameters":[{"name":"application_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","title":"Application Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApplicationPatch"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/payout-account/methods":{"get":{"tags":["Marketplace"],"summary":"List My Payout Methods","description":"Every payout method you hold, PRIMARY FIRST.\n\nThe primary is the one a payout actually lands in. The others are set up\nand waiting; promote one with `/methods/{id}/set-primary`.","operationId":"list_my_payout_methods_marketplace_me_payout_account_methods_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"},"post":{"tags":["Marketplace"],"summary":"Add My Payout Method","description":"Add an ADDITIONAL, non-primary payout method.\n\nREACHES A PAYMENT PROVIDER. Your country decides which: a US person gets a\nnew Stripe Express account created at Stripe; everyone else gets a new Wise\nmethod, with an already-filed W-8 copied onto it so you never re-certify the\nsame person.\n\nCreated NON-PRIMARY. It receives nothing until you promote it. Refused for\nan agency-managed rep - their payout goes to the agency.","operationId":"add_my_payout_method_marketplace_me_payout_account_methods_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/payout-account/methods/{account_id}/set-primary":{"post":{"tags":["Marketplace"],"summary":"Set My Primary Payout Method","description":"Re-point your payouts at a different method.\n\nTHIS CHANGES WHICH BANK ACCOUNT RECEIVES YOUR MONEY. There is exactly one\nprimary; promoting this one demotes the current one in the same swap.","operationId":"set_my_primary_payout_method_marketplace_me_payout_account_methods__account_id__set_primary_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"Payout method id (UUID).","title":"Account Id"},"description":"Payout method id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"marketplace:delete","x-graph8-lifecycle":"active"}},"/marketplace/me/payout-account/methods/{account_id}":{"delete":{"tags":["Marketplace"],"summary":"Delete My Payout Method","description":"Remove a payout method.\n\nRefused for your PRIMARY (you must always have somewhere to be paid - set\nanother primary first) and refused with a 409 while a payout is in flight\nagainst it, because money already in motion would be stranded.","operationId":"delete_my_payout_method_marketplace_me_payout_account_methods__account_id__delete","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"Payout method id (UUID).","title":"Account Id"},"description":"Payout method id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"marketplace:delete","x-graph8-lifecycle":"active"}},"/marketplace/me/payout-account/setup":{"post":{"tags":["Marketplace"],"summary":"Set Up My Payout Account","description":"Create your PRIMARY payout account. REACHES A PAYMENT PROVIDER.\n\nThe first-time path, where `POST /methods` adds a second one. Your profile\ncountry picks the rail: a US person gets a Stripe Express account created at\nStripe, everyone else a Wise method. Idempotent - a second call returns the\naccount that already exists instead of opening another one at Stripe.\n\n400 when your profile has no country (set it with `PATCH /me/profile`\nfirst). Refused for an agency-managed rep - their payout goes to the agency.","operationId":"set_up_my_payout_account_marketplace_me_payout_account_setup_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/payout-account/onboarding-link":{"get":{"tags":["Marketplace"],"summary":"Get My Payout Onboarding Link","description":"A fresh Stripe Express onboarding link for a Stripe payout method.\n\nNOT A PLAIN READ. It creates the Express account at Stripe if the method\ndoes not have one yet, then mints a short-lived hosted link. Stripe-track\nmethods only; a Wise method is refused with a 400.","operationId":"get_my_payout_onboarding_link_marketplace_me_payout_account_onboarding_link_get","parameters":[{"name":"account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Payout method id. Omit to act on your PRIMARY method - the one money is sent to today.","title":"Account Id"},"description":"Payout method id. Omit to act on your PRIMARY method - the one money is sent to today."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/payout-account/login-link":{"get":{"tags":["Marketplace"],"summary":"Get My Payout Login Link","description":"A single-use login link into your Stripe Express dashboard.\n\nTHE LINK IS A CREDENTIAL. Anyone holding it reaches the Stripe account your\npayouts land in. Treat the response like a password, not like a URL.","operationId":"get_my_payout_login_link_marketplace_me_payout_account_login_link_get","parameters":[{"name":"account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Payout method id. Omit to act on your PRIMARY method - the one money is sent to today.","title":"Account Id"},"description":"Payout method id. Omit to act on your PRIMARY method - the one money is sent to today."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/payout-account/fallback":{"post":{"tags":["Marketplace"],"summary":"Fall Back To Wise","description":"Move off Stripe onto Wise. NOT REVERSIBLE FROM THIS SURFACE.\n\nUS-taxable talent are refused (403) - Stripe is the compliance path there.\nFor everyone else this rewrites the payout rail across all three sources of\ntruth at once, and any Stripe Express account you had is ORPHANED: it is left\nin place for an operator to deauthorize by hand, and there is no route here\nthat switches back.","operationId":"fall_back_to_wise_marketplace_me_payout_account_fallback_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"marketplace:delete","x-graph8-lifecycle":"active"}},"/marketplace/me/payout-account/w8-status":{"get":{"tags":["Marketplace"],"summary":"Get My W8 Status","description":"Whether your W-8 is on file, and when it was filed.\n\nA boolean and a timestamp. The certified payload itself is write-only and\nis never returned by any published route.","operationId":"get_my_w8_status_marketplace_me_payout_account_w8_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/me/payout-account/w8-certify":{"post":{"tags":["Marketplace"],"summary":"Certify My W8","description":"File your W-8BEN. Required before bank details on the Wise rail.\n\n`signature` must match `legal_name`, and `certify_checkbox` must be true -\nit IS the certification. Stored encrypted; the response carries no PII back.\nA 503 means the encryption key is unavailable, which is retryable.","operationId":"certify_my_w8_marketplace_me_payout_account_w8_certify_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/W8CertifyRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/payout-account/bank-requirements":{"get":{"tags":["Marketplace"],"summary":"Get My Bank Requirements","description":"What `bank-details` must contain for this currency.\n\nCall this FIRST. The field list comes live from the payment provider and is\nnot the same for two currencies; guessing it produces a 422 from the\nprovider with its own wording rather than anything this contract controls.","operationId":"get_my_bank_requirements_marketplace_me_payout_account_bank_requirements_get","parameters":[{"name":"currency","in":"query","required":true,"schema":{"type":"string","minLength":3,"maxLength":3,"description":"ISO 4217, e.g. `GBP`. The required fields DIFFER per currency.","title":"Currency"},"description":"ISO 4217, e.g. `GBP`. The required fields DIFFER per currency."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/me/payout-account/bank-details":{"post":{"tags":["Marketplace"],"summary":"Submit My Bank Details","description":"Create the payee record money is sent to. REACHES WISE.\n\nThe provider has no idempotency key here, so the server holds a row lock\nacross validation and creation: a retried request short-circuits on the\nexisting recipient (`already_exists: true`) instead of creating a second\npayee. Send `details` exactly as `bank-requirements` asked for it.\n\nRequires a filed W-8 first (400 otherwise).","operationId":"submit_my_bank_details_marketplace_me_payout_account_bank_details_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BankDetailsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/payouts":{"get":{"tags":["Marketplace"],"summary":"List My Payouts","description":"Money that actually moved, plus chargeback deductions.\n\n`net_balance` is the running figure AFTER deductions, which is why it is a\nseparate field rather than something to sum from the rows.","operationId":"list_my_payouts_marketplace_me_payouts_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/me/service-statements":{"post":{"tags":["Marketplace"],"summary":"Create My Service Statement","description":"Open a draft statement for one of your engagements.\n\nTHE PERIOD IS SERVER-DERIVED and any you send is ignored: an active\nengagement bills the previous complete calendar month, a terminated one\nbills its earliest unbilled month. The retainer is PRORATED to the days the\nengagement was actually live, and the meeting lines are generated from the\nengagement's own rate, so `amount` is the sum of the lines and never a typed\nfigure. Add commission / bonus / expense / discount lines, then submit.\n\n409 when a statement already exists for that period. 403 on an\nagency-managed engagement - the agency authors those.","operationId":"create_my_service_statement_marketplace_me_service_statements_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StatementCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"},"get":{"tags":["Marketplace"],"summary":"List My Service Statements","description":"Your own statements, newest first.\n\n`billed_period_start` / `billed_period_end` are the days ACTUALLY billed -\nthe calendar period clamped to the engagement - so a rep who started on the\n12th does not read as having billed a whole month.\n\nAn account with no marketplace profile gets an empty list, not a 404.","operationId":"list_my_service_statements_marketplace_me_service_statements_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"draft | submitted | changes_requested | rejected | approved","title":"Status"},"description":"draft | submitted | changes_requested | rejected | approved"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/me/service-statements/{statement_id}":{"get":{"tags":["Marketplace"],"summary":"Get My Service Statement","description":"One of your own statements.\n\nOn an agency-managed engagement the client-side amounts are REDACTED: the\nagency sets the bill rate and the rep is not permitted to see it.","operationId":"get_my_service_statement_marketplace_me_service_statements__statement_id__get","parameters":[{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Marketplace"],"summary":"Update My Service Statement","description":"Edit a draft's free text.\n\nOnly `summary` and `activities` take effect. Sending only ignored fields is\na 400 (\"no editable fields\"), which is deliberate: it tells you the change\ndid not happen instead of returning 200 over a no-op.","operationId":"update_my_service_statement_marketplace_me_service_statements__statement_id__patch","parameters":[{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StatementUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Marketplace"],"summary":"Delete My Service Statement","description":"Discard a draft. Only in `draft`, only while unlocked.\n\nThe app answers 204 with no body; this returns the envelope with\n`deleted: true` so every published response is an `ApiResponse`.","operationId":"delete_my_service_statement_marketplace_me_service_statements__statement_id__delete","parameters":[{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"marketplace:delete","x-graph8-lifecycle":"active"}},"/marketplace/me/service-statements/{statement_id}/submit":{"post":{"tags":["Marketplace"],"summary":"Submit My Service Statement","description":"ISSUE THE BILL. draft -> submitted.\n\nThis is the money call on the talent side: the statement locks, the client\nis notified, and their review window opens. Approval from there creates the\nclient invoice and the payout. Get the line items right first - after this\nthe talent can only revise a statement the client sends BACK.","operationId":"submit_my_service_statement_marketplace_me_service_statements__statement_id__submit_post","parameters":[{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/service-statements/{statement_id}/revise":{"post":{"tags":["Marketplace"],"summary":"Revise My Service Statement","description":"Reopen a rejected or changes-requested statement for editing.\n\nOnly from `rejected` or `changes_requested`; anything else is a 400. A 409\nmeans it moved underneath you.","operationId":"revise_my_service_statement_marketplace_me_service_statements__statement_id__revise_post","parameters":[{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/service-statements/{statement_id}/line-items":{"get":{"tags":["Marketplace"],"summary":"List My Statement Line Items","description":"Every line on the statement, system-seeded and self-added alike.\n\nGated, not just the writes: the retainer line's `unit_amount_usd` IS the\nclient's monthly rate, which an agency-managed rep may not see.","operationId":"list_my_statement_line_items_marketplace_me_service_statements__statement_id__line_items_get","parameters":[{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"},"post":{"tags":["Marketplace"],"summary":"Add My Statement Line Item","description":"Add one money line to a draft. The statement total is RECOMPUTED.\n\n`retainer` and `meeting` are seeded by the server from the engagement and\ncannot be added by hand. Only `discount` may carry a negative unit amount.\nWritable in `draft` and `changes_requested`; anything later is locked.","operationId":"add_my_statement_line_item_marketplace_me_service_statements__statement_id__line_items_post","parameters":[{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LineItemCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/service-statements/{statement_id}/line-items/{item_id}":{"delete":{"tags":["Marketplace"],"summary":"Delete My Statement Line Item","description":"Remove one of your own added lines. System lines cannot be removed.","operationId":"delete_my_statement_line_item_marketplace_me_service_statements__statement_id__line_items__item_id__delete","parameters":[{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"item_id","in":"path","required":true,"schema":{"type":"string","description":"Line item id (UUID).","title":"Item Id"},"description":"Line item id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"marketplace:delete","x-graph8-lifecycle":"active"}},"/marketplace/org/service-statements":{"get":{"tags":["Marketplace"],"summary":"List Org Service Statements","description":"Statements billed TO your organisation.\n\nEach row carries the talent's name, the days actually billed, and an\n`invoice` block with the hosted payment URL and PDF once one exists. The org\nis the key's own - there is no parameter for it.","operationId":"list_org_service_statements_marketplace_org_service_statements_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/org/service-statements/{statement_id}":{"get":{"tags":["Marketplace"],"summary":"Get Org Service Statement","description":"One statement billed to your org, with who authored it. 404 otherwise.","operationId":"get_org_service_statement_marketplace_org_service_statements__statement_id__get","parameters":[{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/org/service-statements/{statement_id}/line-items":{"get":{"tags":["Marketplace"],"summary":"List Org Statement Line Items","description":"What you are being charged for, line by line.","operationId":"list_org_statement_line_items_marketplace_org_service_statements__statement_id__line_items_get","parameters":[{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"},"post":{"tags":["Marketplace"],"summary":"Add Org Statement Line Item","description":"Adjust a statement you are reviewing. CHANGES WHAT YOU WILL PAY.\n\nAllowed only while `submitted` - once approved the statement is locked. Use\na `discount` line to reduce it; `retainer` and `meeting` are system lines\nand cannot be added.","operationId":"add_org_statement_line_item_marketplace_org_service_statements__statement_id__line_items_post","parameters":[{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LineItemCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/org/service-statements/{statement_id}/line-items/{item_id}":{"delete":{"tags":["Marketplace"],"summary":"Delete Org Statement Line Item","description":"Remove an adjustment line you added. Only while `submitted`.","operationId":"delete_org_statement_line_item_marketplace_org_service_statements__statement_id__line_items__item_id__delete","parameters":[{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"item_id","in":"path","required":true,"schema":{"type":"string","description":"Line item id (UUID).","title":"Item Id"},"description":"Line item id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"marketplace:delete","x-graph8-lifecycle":"active"}},"/marketplace/org/service-statements/{statement_id}/checkout-url":{"get":{"tags":["Marketplace"],"summary":"Get Org Statement Checkout Url","description":"The hosted payment link for an approved statement's invoice.\n\nA READ: it returns a URL that already exists and creates nothing. 404 until\nthe statement has an invoice, 400 once that invoice is already paid.","operationId":"get_org_statement_checkout_url_marketplace_org_service_statements__statement_id__checkout_url_get","parameters":[{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/org/service-statements/{statement_id}/request-changes":{"post":{"tags":["Marketplace"],"summary":"Request Changes On Org Statement","description":"Send a submitted statement back with notes, instead of approving it.\n\nThe softer of the two refusals: it returns the statement to the author to\nrevise and resubmit, rather than rejecting it outright. Only from\n`submitted`; 409 if someone already acted on it.","operationId":"request_changes_on_org_statement_marketplace_org_service_statements__statement_id__request_changes_post","parameters":[{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StatementDecisionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/org/service-statements/{statement_id}/approve":{"post":{"tags":["Marketplace"],"summary":"Approve Org Service Statement","description":"APPROVE THE BILL. submitted -> approved, and the statement locks.\n\nThis is the money call on the client side: approval creates the client\ninvoice that your organisation is charged, and the talent's payout follows\nfrom it. It cannot be undone from this surface.\n\nAdmin-gated, like `POST /marketplace/org/invoices/{invoice_id}/approve`:\nthe caller must be an Admin or Owner of the org, on a personal key.\nOrg-scoped machine keys are refused, because a key with no human behind it\nshould not be able to commit the org to a charge. Only from `submitted`; a\n409 means somebody already acted on it.","operationId":"approve_org_service_statement_marketplace_org_service_statements__statement_id__approve_post","parameters":[{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/org/service-statements/{statement_id}/reject":{"post":{"tags":["Marketplace"],"summary":"Reject Org Service Statement","description":"REFUSE the bill outright, with a reason the talent sees.\n\nThe harder of the two refusals (`request-changes` is the softer one): the\nstatement goes to `rejected`. The talent can still revise and resubmit it,\nbut nothing is billed from it until they do. Admin-gated for the same\nreason approval is - accepting and refusing a bill are the same decision.","operationId":"reject_org_service_statement_marketplace_org_service_statements__statement_id__reject_post","parameters":[{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StatementDecisionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/commissions/plans":{"get":{"tags":["Marketplace"],"summary":"List Commission Plans","description":"Every commission plan version your org holds, newest first.\n\nVersions are immutable once written; a change is a NEW version against the\nsame `plan_id`. Only an `active` version can be snapshotted onto a hire.","operationId":"list_commission_plans_marketplace_commissions_plans_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"},"post":{"tags":["Marketplace"],"summary":"Create Commission Plan","description":"Write a new plan version. Created as `draft`; activate it separately.\n\nPass `previous_version_id` to supersede an existing plan - the new row keeps\nthat plan's `plan_id` and takes the next version number. Omit it to start a\nnew plan.","operationId":"create_commission_plan_marketplace_commissions_plans_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NewPlan"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/commissions/plans/{version_id}/activate":{"post":{"tags":["Marketplace"],"summary":"Activate Commission Plan","description":"Put a plan version IN FORCE.\n\nFrom here on it is the formula every new engagement snapshots, so it decides\nwhat people are paid. The terms are re-validated on the way in; an\nunparseable version cannot be activated.","operationId":"activate_commission_plan_marketplace_commissions_plans__version_id__activate_post","parameters":[{"name":"version_id","in":"path","required":true,"schema":{"type":"string","description":"Plan version id (UUID).","title":"Version Id"},"description":"Plan version id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/commissions/preview":{"post":{"tags":["Marketplace"],"summary":"Preview Commission","description":"Dry-run a plan against one collection. Writes nothing, pays nobody.\n\nSend the `terms` you are about to save and a sample `collection`; the answer\nis exactly what `POST /commissions/entries` would compute for it. Use it\nbefore activating a plan version, because activation is the act that\ndecides what people are paid. An unparseable plan is a 422.","operationId":"preview_commission_marketplace_commissions_preview_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Preview"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/commissions/entries":{"get":{"tags":["Marketplace"],"summary":"List Commission Entries","description":"Recorded earnings, newest first, capped at 500 by the app.","operationId":"list_commission_entries_marketplace_commissions_entries_get","parameters":[{"name":"hiring_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Restrict to one engagement (UUID).","title":"Hiring Id"},"description":"Restrict to one engagement (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"},"post":{"tags":["Marketplace"],"summary":"Record Commission Entry","description":"Record a collection and compute what it earned. MONEY NOW OWED.\n\nCalculated against the plan SNAPSHOTTED on the engagement at signature, not\nagainst whatever is active today, so re-pricing never re-prices history.\nIdempotent on `(event_id, invoice_line_id)`: the same collection replayed\nreturns the existing entry, and the SAME ids with different evidence is a\n409 rather than a second payment.\n\nLands in `review`. It becomes payable when allocated to a statement.","operationId":"record_commission_entry_marketplace_commissions_entries_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NewEntry"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/commissions/entries/{entry_id}/statement":{"post":{"tags":["Marketplace"],"summary":"Allocate Commission Entry","description":"PUT THE EARNING ON A BILL.\n\nWrites the entry as a line item on the statement, which is what turns a\nrecorded earning into something actually paid. The statement is scoped\nthrough the entry's OWN engagement, never an org id from the body, so an\nentry cannot be allocated onto someone else's statement.\n\nRefused once the statement is locked for review or payment, and refused if\nthe correction would take its total negative. Re-allocating to the same\nstatement is idempotent; to a different one it is a 409.","operationId":"allocate_commission_entry_marketplace_commissions_entries__entry_id__statement_post","parameters":[{"name":"entry_id","in":"path","required":true,"schema":{"type":"string","description":"Commission entry id (UUID).","title":"Entry Id"},"description":"Commission entry id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Allocate"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/commissions/entries/{entry_id}/quality":{"post":{"tags":["Marketplace"],"summary":"Resolve Commission Quality","description":"RELEASE OR REFUSE A HELD AMOUNT.\n\nOnly the quality decision and its evidence may change - resend the original\ncollection otherwise identical, or it is a 422. If the entry is already on a\nstatement the release arrives as a NEW reviewable entry rather than editing\na bill in flight, which is why an approved decision can create a second row.","operationId":"resolve_commission_quality_marketplace_commissions_entries__entry_id__quality_post","parameters":[{"name":"entry_id","in":"path","required":true,"schema":{"type":"string","description":"Commission entry id (UUID).","title":"Entry Id"},"description":"Commission entry id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Collection"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/commissions/entries/{entry_id}/reversals":{"post":{"tags":["Marketplace"],"summary":"Reverse Commission Entry","description":"CLAW BACK earnings against a refund. Writes a negative entry.\n\nNever edits the original - the ledger stays append-only, which is what makes\nit auditable. Reversals cannot exceed the original in total, and the same\n`event_id` replayed returns the existing correction rather than doubling it.","operationId":"reverse_commission_entry_marketplace_commissions_entries__entry_id__reversals_post","parameters":[{"name":"entry_id","in":"path","required":true,"schema":{"type":"string","description":"The POSITIVE entry being corrected (UUID).","title":"Entry Id"},"description":"The POSITIVE entry being corrected (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Reversal"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/rates":{"put":{"tags":["Marketplace"],"summary":"Update My Rate Card","description":"Publish the rate card. THIS IS THE PRICE A CLIENT IS BILLED.\n\nThe narrow sibling of `PATCH /marketplace/me/profile`, kept because it is\nwhat the rates surface calls; both apply the same agency lock and the same\navailability vocabulary. Set `availability_status` to `hidden` to come off\nthe browse list without deactivating anything.","operationId":"update_my_rate_card_marketplace_me_rates_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RateCardUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/agency":{"get":{"tags":["Marketplace"],"summary":"Get My Agency","description":"The agency this account OPERATES, or null.\n\nAnswers the one question the agency console is gated on. `{\"agency\": null}`\nfor an ordinary talent or a client - and also while the talent-agencies\nfeature is dark, deliberately, so a disabled feature reads as absent rather\nthan as a console in which nothing works.","operationId":"get_my_agency_marketplace_me_agency_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/me/contracts":{"get":{"tags":["Marketplace"],"summary":"List My Marketplace Contracts","description":"EVERY contract of yours - pending, active and terminated - with client names.\n\nWider than the published `/marketplace/me/offers`, which returns only what\nis still pending. Rows on an agency-managed engagement have the client's\nrate redacted: the agency prices those and the rep is paid by the agency.","operationId":"list_my_marketplace_contracts_marketplace_me_contracts_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/me/invoices/{invoice_id}":{"put":{"tags":["Marketplace"],"summary":"Annotate My Invoice","description":"Annotate your own draft invoice before approving it.\n\nOnly while the invoice is in `sdr_review` - after\n`POST /marketplace/me/invoices/{id}/approve` the client's review window is\nopen and the figures are theirs to dispute, not yours to re-explain. Only\n`sdr_notes` is writable; `client_notes` and `dispute_reason` belong to the\npaying side.","operationId":"annotate_my_invoice_marketplace_me_invoices__invoice_id__put","parameters":[{"name":"invoice_id","in":"path","required":true,"schema":{"type":"string","description":"Invoice id (UUID). Must be yours.","title":"Invoice Id"},"description":"Invoice id (UUID). Must be yours."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/InvoiceNotesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/connect/onboarding-link":{"get":{"tags":["Marketplace"],"summary":"Get My Connect Onboarding Link","description":"A fresh Stripe Express onboarding link.\n\nNOT A PLAIN READ: if you have no Express account yet it CREATES one at\nStripe first (idempotency-keyed on your profile id, so a retry does not mint\na second). Refused with a 400 on the Wise rail, where onboarding is the W-8\nplus bank-details flow on the payout-account surface instead.","operationId":"get_my_connect_onboarding_link_marketplace_me_connect_onboarding_link_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/connect/dashboard-link":{"get":{"tags":["Marketplace"],"summary":"Get My Connect Dashboard Link","description":"A login link into your Stripe Express dashboard.\n\nTHE LINK IS A CREDENTIAL - it logs the holder into the Stripe account your\npayouts land in. Pre-checked against live Stripe state: a non-Express or\nnot-yet-onboarded account is a 400 explaining which, rather than a link that\ndead-ends.","operationId":"get_my_connect_dashboard_link_marketplace_me_connect_dashboard_link_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/headshot":{"post":{"tags":["Marketplace"],"summary":"Upload My Headshot","description":"Upload your profile photo. `multipart/form-data`.\n\nA headshot OR a resume is one of the three gates on going live to buyers -\nsee `completeness.blocking_reasons` on `PATCH /marketplace/me/profile`.\n`headshot_source` in the response says whether the stored image is yours or\nthe generated initials fallback.","operationId":"upload_my_headshot_marketplace_me_headshot_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_my_headshot_marketplace_me_headshot_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/resume":{"post":{"tags":["Marketplace"],"summary":"Upload My Resume","description":"Upload your resume and let it fill in your profile. `multipart/form-data`.\n\nThe text is extracted and parsed by a model into `work_experience`,\nstrengths, industries, tools, `summary` and `tagline`. Those AI-derived\nfields are OVERWRITTEN on every upload; anything you typed yourself is kept.\ngraph8 carries the parsing cost - no credits are charged. If extraction\nfails the file is still stored and `message` says so.","operationId":"upload_my_resume_marketplace_me_resume_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_my_resume_marketplace_me_resume_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/video-intro":{"post":{"tags":["Marketplace"],"summary":"Upload My Video Intro","description":"Upload a video introduction. `multipart/form-data`.\n\nReplacing one leaves the previous object in storage rather than deleting it\nfirst, so the profile never points at nothing mid-upload. The new URL is\nstamped as a deliberate edit, which protects it from being overwritten by a\nlater resume re-import.","operationId":"upload_my_video_intro_marketplace_me_video_intro_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_my_video_intro_marketplace_me_video_intro_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/sync-workbench":{"post":{"tags":["Marketplace"],"summary":"Sync My Workbench","description":"Pull the AI assessment of your resume onto your profile.\n\nIdempotent and safe to poll: it finds the LATEST analysed upload (so a\nre-upload supersedes the cached one), copies the derived fields across,\nand NEVER overwrites a field you edited yourself. `synced: false` with a\nmessage means the pipeline has not finished, not that anything failed.\n\nThis is what produces the certification score, and the score is the third\ngate on being visible to buyers - which is why the sync is a call you can\nmake rather than something to wait on.","operationId":"sync_my_workbench_marketplace_me_sync_workbench_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/wizard-status":{"get":{"tags":["Marketplace"],"summary":"Get My Wizard Status","description":"Per-step onboarding progress, computed from the profile each call.\n\nStateless - nothing is stored, so it cannot go stale against the profile it\ndescribes. `is_marketplace_ready` tolerates ONE incomplete step because the\nvideo introduction is optional.","operationId":"get_my_wizard_status_marketplace_me_wizard_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/me/work-certificates":{"post":{"tags":["Marketplace"],"summary":"Issue My Work Certificate","description":"Issue verifiable proof of a finished engagement.\n\nIDEMPOTENT: when nothing about the engagement has changed you get the\nEXISTING certificate back rather than a second code, so a retry cannot leave\ntwo certificates in circulation for one piece of work. 409 if the engagement\nis not a signed active/completed one, or if its certificate was revoked.\n\nThe certificate carries a code a third party verifies; the app's public\nverification route is deliberately not published here (see the router\ndocstring in `marketplace_agency_router` for the cross-org rule).","operationId":"issue_my_work_certificate_marketplace_me_work_certificates_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkCertificateIssueRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"},"get":{"tags":["Marketplace"],"summary":"List My Work Certificates","description":"Every certificate you hold, including revoked ones.\n\nRevoked rows are returned rather than hidden: a certificate you circulated\nthat has since been revoked is exactly the thing you need to know about.","operationId":"list_my_work_certificates_marketplace_me_work_certificates_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/contracts/{hiring_id}":{"get":{"tags":["Marketplace"],"summary":"Get Marketplace Contract","description":"The contract for a hiring: body, signature state, and the key terms.\n\nReadable by the two PARTIES only - the client org that sent it, or the\ntalent it was sent to. Anyone else gets 404 rather than 403, so hiring ids\ncannot be enumerated by watching the status code change. `caller_role` in\nthe response says which side you resolved as.\n\n`envelope.signer_token` is returned to the TALENT only and is the secret the\nsigning call needs; the client never sees it, because holding it would let\nthem sign in the talent's stead.","operationId":"get_marketplace_contract_marketplace_contracts__hiring_id__get","parameters":[{"name":"hiring_id","in":"path","required":true,"schema":{"type":"string","description":"Hiring id (UUID).","title":"Hiring Id"},"description":"Hiring id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/terms-acknowledgements/pending":{"get":{"tags":["Marketplace"],"summary":"List Pending Terms Acknowledgements","description":"Terms documents waiting on your acknowledgement.\n\nAnswers for whichever side you are: a client org's pending rows AND, if the\nsame principal also has a marketplace profile, the talent-side rows. A\nnon-empty result is what the re-consent prompt is driven by.","operationId":"list_pending_terms_acknowledgements_marketplace_terms_acknowledgements_pending_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/terms-acknowledgements/ack-all":{"post":{"tags":["Marketplace"],"summary":"Acknowledge All Pending Terms","description":"Acknowledge every pending terms document in one transaction.\n\nTHIS IS A LEGAL ACT. The document VERSIONS are resolved server-side from\nwhat the runtime currently considers current, never from anything the caller\nclaims, and the row is stamped with the request's IP and user agent.\n\n`request` is forwarded because the handler reads exactly those two things\noff it; calling without it is a missing-argument TypeError rather than a\nmissing audit field.","operationId":"acknowledge_all_pending_terms_marketplace_terms_acknowledgements_ack_all_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/opportunities":{"get":{"tags":["Marketplace"],"summary":"List Marketplace Opportunities","description":"Published roles, newest first, each with YOUR fit pre-score.\n\nThe pre-score is deterministic and free - it is computed from your profile\nagainst the role, not by a model, so listing costs nothing. The hiring org\nis not named until you are in conversation with it.","operationId":"list_marketplace_opportunities_marketplace_opportunities_get","parameters":[{"name":"role_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Restrict to one role type, e.g. `sdr`.","title":"Role Type"},"description":"Restrict to one role type, e.g. `sdr`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/opportunities/{post_id}":{"get":{"tags":["Marketplace"],"summary":"Get Marketplace Opportunity","description":"One published role with your fit pre-score. 404 once it is unpublished.","operationId":"get_marketplace_opportunity_marketplace_opportunities__post_id__get","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"Job post id (UUID).","title":"Post Id"},"description":"Job post id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/opportunities/{post_id}/apply":{"post":{"tags":["Marketplace"],"summary":"Apply To Marketplace Opportunity","description":"Apply to a role. The hiring org sees the application and is notified.\n\nOne application per role; applying twice is refused rather than duplicated.","operationId":"apply_to_marketplace_opportunity_marketplace_opportunities__post_id__apply_post","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"Job post id (UUID).","title":"Post Id"},"description":"Job post id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OpportunityApplyRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/applications":{"get":{"tags":["Marketplace"],"summary":"List My Marketplace Applications","description":"Every role you applied to, with where each application stands.","operationId":"list_my_marketplace_applications_marketplace_me_applications_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/me/mcp-access":{"get":{"tags":["Marketplace"],"summary":"Get My Mcp Access","description":"Whether graph8 MCP access is active on your talent account.\n\nA read: `activated`, the trial state, and `banked_months` - referral months\nearned before activation that apply automatically when it happens.\nActivating is not published here; see the router docstring.","operationId":"get_my_mcp_access_marketplace_me_mcp_access_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/agencies":{"get":{"tags":["Marketplace"],"summary":"List Talent Agencies","description":"Every active agency, with roster statistics.\n\nCounts are computed over each agency's VISIBLE roster, so an agency never\nadvertises reps a buyer cannot actually browse to.","operationId":"list_talent_agencies_marketplace_agencies_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}":{"get":{"tags":["Marketplace"],"summary":"Get Talent Agency","description":"One agency's public summary. 404 when the slug is unknown or inactive.","operationId":"get_talent_agency_marketplace_agencies__slug__get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Marketplace"],"summary":"Update Agency Profile","description":"Edit your own agency's branding. Agency account only.\n\nFour display fields and nothing else - never `status`, `owner_org_id`,\n`agency_profile_id` or `billing_email`, because those decide who gets paid\nand whether the agency exists at all. An empty body is a 400 rather than a\nsilent no-op.","operationId":"update_agency_profile_marketplace_agencies__slug__patch","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgencyProfileUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}/roster":{"get":{"tags":["Marketplace"],"summary":"Get Agency Roster","description":"Every rep bound to this agency, listed or not.\n\nDeliberately UNFILTERED by browse visibility: the reps that most need\nattention are the ones not yet live. Each row carries `ready_to_publish`\nplus a per-rep `missing` field list, so thirty drafts do not have to be\nopened one by one to find the three without a country.\n\nArchived reps are flagged rather than dropped - they are still needed to put\na name on an old statement or payout row - and every count excludes them.","operationId":"get_agency_roster_marketplace_agencies__slug__roster_get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}/intake":{"get":{"tags":["Marketplace"],"summary":"Get Agency Intake","description":"Every resume this agency's intake saw, and what became of each one.\n\nAnswers \"I sent thirty CVs and I can see eleven reps - where are the other\nnineteen?\", which is otherwise unanswerable: the pipeline used to compute a\ndecline reason and throw it into a log line.\n\nRead `summary.total` and `summary.truncated`, not `len(items)` - the reason\nbreakdown is computed over the page, and a 600-event history paged at 500\nwould otherwise read as a complete picture.","operationId":"get_agency_intake_marketplace_agencies__slug__intake_get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"description":"Newest first. Capped at 500.","default":100,"title":"Limit"},"description":"Newest first. Capped at 500."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}/intake/upload":{"post":{"tags":["Marketplace"],"summary":"Upload Agency Resumes","description":"Add reps by uploading their resumes. `multipart/form-data`.\n\nThe same pipeline as the agency's intake mailbox, over HTTPS - and the more\nreliable of the two, because an upload arrives already authenticated as the\nagency rather than routed by an email slug.\n\nREPORTS PER FILE, NOT PER BATCH. Read each outcome: a batch that fails as a\nunit makes an agency guess which three of thirty were rejected. Nothing here\nactivates anybody - the profiles are built, then completed with\n`PATCH /reps/{id}` and listed with `POST /reps/{id}/publish`.\n\n409 until the agency's intake has proved end to end that it can process a\nresume at all.","operationId":"upload_agency_resumes_marketplace_agencies__slug__intake_upload_post","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_agency_resumes_marketplace_agencies__slug__intake_upload_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}/reps/{sdr_id}":{"patch":{"tags":["Marketplace"],"summary":"Edit Agency Rep","description":"Complete or correct one of your own reps.\n\nThe response is the useful part: `updated` is what landed, `refused` names\nwhat did not and why, and `missing` / `missing_summary` say what still\nstands between this rep and being publishable. A request whose fields are\nALL forbidden is a 403; one with no editable fields at all is a 400.\n\nAssessment fields (certification score, dimensions) are server-owned and\nalways refused - an agency does not score its own reps.","operationId":"edit_agency_rep_marketplace_agencies__slug__reps__sdr_id__patch","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"sdr_id","in":"path","required":true,"schema":{"type":"string","description":"Rep profile id (UUID). Must be on this agency's roster.","title":"Sdr Id"},"description":"Rep profile id (UUID). Must be on this agency's roster."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Editable profile fields. The server owns the allow-list and REFUSES a forbidden field BY NAME in `refused` rather than dropping it, so a rejected edit is visible instead of looking like it worked.","title":"Updates"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Marketplace"],"summary":"Remove Agency Rep","description":"Take a rep off your roster.\n\n409 while they are on an ACTIVE placement or have a contract out for\nsignature. That ordering is the point: ending the placement is what revokes\ntheir seat in the client's workspace, and archiving the listing first would\nleave somebody with live access to a client's CRM and no agency accountable\nfor them.\n\nThe listing is archived rather than reverted to independent talent - an\nagency rep has no account, no payout record and no terms of their own, so\nthere is nothing to revert to.","operationId":"remove_agency_rep_marketplace_agencies__slug__reps__sdr_id__delete","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"sdr_id","in":"path","required":true,"schema":{"type":"string","description":"Rep profile id (UUID). Must be on this agency's roster.","title":"Sdr Id"},"description":"Rep profile id (UUID). Must be on this agency's roster."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"marketplace:delete","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}/reps/{sdr_id}/publish":{"post":{"tags":["Marketplace"],"summary":"Publish Agency Rep","description":"List a completed rep on the marketplace, at the price you set.\n\nConsole-built reps deliberately do NOT auto-activate, and this is why: the\ntier fallback would otherwise derive a rate nobody at the agency chose and\nput a person on a public marketplace at it. Publishing is where the agency\nexercises its pricing authority.\n\nRefused with the specific missing fields rather than \"incomplete\".","operationId":"publish_agency_rep_marketplace_agencies__slug__reps__sdr_id__publish_post","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"sdr_id","in":"path","required":true,"schema":{"type":"string","description":"Rep profile id (UUID). Must be on this agency's roster.","title":"Sdr Id"},"description":"Rep profile id (UUID). Must be on this agency's roster."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}/contracts":{"get":{"tags":["Marketplace"],"summary":"Get Agency Contracts","description":"Contracts awaiting signature, and those already signed.\n\nDerived from the placements rather than stored separately, so the two can\nnever disagree about the same engagement.","operationId":"get_agency_contracts_marketplace_agencies__slug__contracts_get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}/payouts":{"get":{"tags":["Marketplace"],"summary":"Get Agency Payouts","description":"Payouts the agency received, attributed to the rep who earned each one.\n\nAttribution comes through the service statement, NOT the payout row: the\npayout names the agency as payee, so grouping on it would collapse the whole\nroster onto one line.","operationId":"get_agency_payouts_marketplace_agencies__slug__payouts_get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":100,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}/placements/{hiring_id}/end":{"post":{"tags":["Marketplace"],"summary":"End Agency Placement","description":"End one of your placements. NOT REVERSIBLE.\n\nThe agency's door to the act the client already had. One call covers both\nshapes: an ACTIVE placement is terminated, a still-unsigned offer is\nwithdrawn and its contract envelope VOIDED so the signing page goes dead.\nAnything else is a 400 naming the state, and a 409 means it moved underneath\nyou - a lost race must never report success, or you believe an offer is dead\nwhile it is still signable.\n\nTerminating also REVOKES the rep's seat in the client's workspace - their\nonly access to graph8 - and notifies the client, who has just lost their rep\nmid-engagement. Withdrawing does not, because an unsigned offer never\ngranted one.","operationId":"end_agency_placement_marketplace_agencies__slug__placements__hiring_id__end_post","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"hiring_id","in":"path","required":true,"schema":{"type":"string","description":"Placement/hiring id (UUID).","title":"Hiring Id"},"description":"Placement/hiring id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"marketplace:delete","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}/service-statements":{"post":{"tags":["Marketplace"],"summary":"Create Agency Statement","description":"Draft a statement for one of your reps.\n\nThe SAME server-derived period and system-seeded retainer + meeting lines as\nthe talent path - the agency does not get to pick a billing window or retype\nthe base, only to add to it and submit it. That is what stops two doors\nbilling two different amounts for one month.\n\n409 when every period of the engagement already has a statement.","operationId":"create_agency_statement_marketplace_agencies__slug__service_statements_post","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgencyStatementCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"},"get":{"tags":["Marketplace"],"summary":"List Agency Statements","description":"Statements across the whole roster, newest first.\n\nOne query for the roster rather than one per rep, so an agency operating\nforty people does not pay forty round trips to render a list. Nothing is\nredacted here: the agency sets the rate and collects the money, so there is\nnothing to hide from it.","operationId":"list_agency_statements_marketplace_agencies__slug__service_statements_get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"}},{"name":"sdr_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Restrict to one rep (UUID).","title":"Sdr Id"},"description":"Restrict to one rep (UUID)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}/service-statements/{statement_id}":{"get":{"tags":["Marketplace"],"summary":"Get Agency Statement","description":"One statement, unredacted.\n\nA statement belonging to another agency answers 404 on the ROSTER check, not\n403 on the statement - so its existence is never confirmed.","operationId":"get_agency_statement_marketplace_agencies__slug__service_statements__statement_id__get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Marketplace"],"summary":"Update Agency Statement","description":"Edit a draft's free text. Period and amount are derived, not typed.","operationId":"update_agency_statement_marketplace_agencies__slug__service_statements__statement_id__patch","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AgencyStatementUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}/service-statements/{statement_id}/line-items":{"get":{"tags":["Marketplace"],"summary":"List Agency Statement Line Items","description":"Every line, system-generated and agency-added alike.","operationId":"list_agency_statement_line_items_marketplace_agencies__slug__service_statements__statement_id__line_items_get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"},"post":{"tags":["Marketplace"],"summary":"Add Agency Statement Line Item","description":"Add commission / bonus / expense / discount. RECOMPUTES THE TOTAL.\n\nThis is the money the REP may never put on a client's bill - it belongs to\nthe agency, which is the party with a commercial stake in the amount.\n`retainer` and `meeting` are system-generated from the engagement's rate and\ncannot be added by hand, by anyone.","operationId":"add_agency_statement_line_item_marketplace_agencies__slug__service_statements__statement_id__line_items_post","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LineItemCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}/service-statements/{statement_id}/submit":{"post":{"tags":["Marketplace"],"summary":"Submit Agency Statement","description":"ISSUE THE BILL to the client. draft -> submitted.\n\nRuns the talent path's OWN submit handler with the rep's id, so the\nlifecycle transition, the locking and the downstream invoice trigger are the\nsame code. The agency is authorised to act; it is not a second process.","operationId":"submit_agency_statement_marketplace_agencies__slug__service_statements__statement_id__submit_post","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"statement_id","in":"path","required":true,"schema":{"type":"string","description":"Service statement id (UUID).","title":"Statement Id"},"description":"Service statement id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}/reps/{sdr_id}/unlist":{"post":{"tags":["Marketplace"],"summary":"Unlist Agency Rep","description":"Take a rep off the marketplace WITHOUT taking them off your roster.\n\n\"Hide them for now\", where `DELETE /{slug}/reps/{sdr_id}` is \"they no longer\nwork here\". The rep leaves browse and keeps everything else; `/publish`\nre-lists them through the same readiness check as the first time. Refused\nwhile they are actively placed or have a contract out for signature - end\nthe client relationship first, rather than hiding it.","operationId":"unlist_agency_rep_marketplace_agencies__slug__reps__sdr_id__unlist_post","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"sdr_id","in":"path","required":true,"schema":{"type":"string","description":"Rep profile id (UUID). Must be on this agency's roster.","title":"Sdr Id"},"description":"Rep profile id (UUID). Must be on this agency's roster."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}/reps/{sdr_id}/video-intro":{"post":{"tags":["Marketplace"],"summary":"Upload Agency Rep Video Intro","description":"Upload a rep's intro video on their behalf. `multipart/form-data`.\n\nSame storage and limits as the talent's own upload. An agency rep has no\nlogin, so the agency is the only party that can give them one. Marked as\nagency-supplied, so a later resume re-import cannot overwrite it.","operationId":"upload_agency_rep_video_intro_marketplace_agencies__slug__reps__sdr_id__video_intro_post","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"sdr_id","in":"path","required":true,"schema":{"type":"string","description":"Rep profile id (UUID). Must be on this agency's roster.","title":"Sdr Id"},"description":"Rep profile id (UUID). Must be on this agency's roster."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_agency_rep_video_intro_marketplace_agencies__slug__reps__sdr_id__video_intro_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"},"delete":{"tags":["Marketplace"],"summary":"Clear Agency Rep Video Intro","description":"Remove a rep's intro video from their profile.","operationId":"clear_agency_rep_video_intro_marketplace_agencies__slug__reps__sdr_id__video_intro_delete","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"sdr_id","in":"path","required":true,"schema":{"type":"string","description":"Rep profile id (UUID). Must be on this agency's roster.","title":"Sdr Id"},"description":"Rep profile id (UUID). Must be on this agency's roster."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"marketplace:delete","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}/requests":{"get":{"tags":["Marketplace"],"summary":"Get Agency Open Requests","description":"Client requests for your reps that nobody has answered yet.\n\nYour work queue: who wants whom, and since when. Derived from the message\nthreads, and cleared by an agency reply or by a placement.","operationId":"get_agency_open_requests_marketplace_agencies__slug__requests_get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}/placements":{"get":{"tags":["Marketplace"],"summary":"Get Agency Placements","description":"Where your reps are placed: client, rate, and state.","operationId":"get_agency_placements_marketplace_agencies__slug__placements_get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"active | terminated | pending_acceptance","title":"Status"},"description":"active | terminated | pending_acceptance"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/agencies/{slug}/revenue":{"get":{"tags":["Marketplace"],"summary":"Get Agency Revenue","description":"Money in: settled and pending per rep, and settled per month.","operationId":"get_agency_revenue_marketplace_agencies__slug__revenue_get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"Agency slug, e.g. `netrion-labs`. You must operate it.","title":"Slug"},"description":"Agency slug, e.g. `netrion-labs`. You must operate it."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/conversations":{"get":{"tags":["Marketplace"],"summary":"List Marketplace Conversations","description":"Your organisation's marketplace threads, with the talent's display name.\n\nAn anonymous profile is shown under its stable CODENAME until your org has\nhired them, after which the reveal is permanent. `unread_count`,\n`is_starred`, `is_archived` and `is_spam` are YOUR side's state - the\ntalent's own flags are stripped from the response, not merely hidden.","operationId":"list_marketplace_conversations_marketplace_conversations_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/conversations/{conversation_id}/state":{"patch":{"tags":["Marketplace"],"summary":"Set Marketplace Conversation State","description":"Star, archive or mark spam - on YOUR side of the thread only.\n\nEach flag is explicit rather than a toggle, so a retried request is\nidempotent instead of flipping the state back. Omitted flags are left alone.\nA thread belonging to another org is a 404.","operationId":"set_marketplace_conversation_state_marketplace_conversations__conversation_id__state_patch","parameters":[{"name":"conversation_id","in":"path","required":true,"schema":{"type":"string","description":"Conversation id (UUID).","title":"Conversation Id"},"description":"Conversation id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ConversationStateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/conversations/{conversation_id}/read":{"post":{"tags":["Marketplace"],"summary":"Mark Marketplace Conversation Read","description":"Clear your org's unread count on a thread. Idempotent.","operationId":"mark_marketplace_conversation_read_marketplace_conversations__conversation_id__read_post","parameters":[{"name":"conversation_id","in":"path","required":true,"schema":{"type":"string","description":"Conversation id (UUID).","title":"Conversation Id"},"description":"Conversation id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/talent/{sdr_id}/request":{"post":{"tags":["Marketplace"],"summary":"Request Talent Through Agency","description":"Ask an agency to set up an engagement with one of its reps.\n\nWhat replaces Hire on an agency rep. It deliberately creates NO hiring and\nNO offer: you are not contracting with the rep, and the terms you would\naccept are not the terms that end up signed. It starts the conversation the\nagency needs in order to act, and makes sure they hear about it - message,\nin-app notification and email, delivered to the agency rather than the rep.\n\nIDEMPOTENT BY CONSTRUCTION: the thread is unique per (org, rep), so a second\nrequest appends a second message rather than creating anything. Clicking\ntwice has nudged the agency twice, which is what clicking twice means.\n\n404 for talent who are not agency-bound - they have\n`POST /marketplace/talent/{sdr_id}/hire`, and a second door here would imply\na way to engage them that does not exist.","operationId":"request_talent_through_agency_marketplace_talent__sdr_id__request_post","parameters":[{"name":"sdr_id","in":"path","required":true,"schema":{"type":"string","description":"Talent profile id (UUID). Must be agency-bound.","title":"Sdr Id"},"description":"Talent profile id (UUID). Must be agency-bound."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/messages/{conversation_id}/reply":{"post":{"tags":["Marketplace"],"summary":"Reply To Marketplace Conversation","description":"Reply on a thread. REACHES THE BUYER - notification and email, now.\n\nThe name the buyer sees is decided server-side and burned into the stored\nmessage: an anonymous talent writes under their codename until that buyer\nhas hired them, and an AGENCY account replying on a roster thread is signed\nas the AGENCY, because presenting the rep's name over words the rep did not\nwrite would misrepresent who the buyer is talking to.\n\nAn agency account may reply on any thread of its own roster; everyone else,\nonly on their own. 404 otherwise.","operationId":"reply_to_marketplace_conversation_marketplace_me_messages__conversation_id__reply_post","parameters":[{"name":"conversation_id","in":"path","required":true,"schema":{"type":"string","description":"Conversation id (UUID).","title":"Conversation Id"},"description":"Conversation id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MessageSendRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/messages/{conversation_id}/state":{"patch":{"tags":["Marketplace"],"summary":"Set My Conversation State","description":"Star, archive or mark spam on YOUR side of the thread.\n\nThe mirror of the buyer-side route and a genuinely separate set of columns -\narchiving here does not archive it for the buyer.","operationId":"set_my_conversation_state_marketplace_me_messages__conversation_id__state_patch","parameters":[{"name":"conversation_id","in":"path","required":true,"schema":{"type":"string","description":"Conversation id (UUID).","title":"Conversation Id"},"description":"Conversation id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ConversationStateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/messages/{conversation_id}/read":{"post":{"tags":["Marketplace"],"summary":"Mark My Conversation Read","description":"Clear your own unread count on a thread. Idempotent.","operationId":"mark_my_conversation_read_marketplace_me_messages__conversation_id__read_post","parameters":[{"name":"conversation_id","in":"path","required":true,"schema":{"type":"string","description":"Conversation id (UUID).","title":"Conversation Id"},"description":"Conversation id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/org/hirings/{hiring_id}/meetings":{"post":{"tags":["Marketplace"],"summary":"Create Org Hiring Meeting","description":"Log a meeting that happened outside the integrated calendar.\n\nA BILLING INPUT, not just a record: the per-meeting rate bills meetings that\nreach `status='taken'`. This creates the row in `scheduled` and attributes\nit to the client; moving it to `taken` is a separate, client-owned\ntransition, so recording a meeting here does not by itself bill for one.\n\nBeside it sits `/marketplace/org/hirings/{hiring_id}`, which is the same\nhiring - the meeting is scoped to it and to your org, and a hiring belonging\nto another org is refused.","operationId":"create_org_hiring_meeting_marketplace_org_hirings__hiring_id__meetings_post","parameters":[{"name":"hiring_id","in":"path","required":true,"schema":{"type":"string","description":"Your org's hiring id (UUID).","title":"Hiring Id"},"description":"Your org's hiring id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MeetingCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/job-posts/{post_id}/jd":{"post":{"tags":["Marketplace"],"summary":"Upload Job Post Jd","description":"Attach the job description PDF to one of your roles. `multipart/form-data`.\n\nThe last missing piece of the already-published `/marketplace/job-posts/*`\nlifecycle: a role could be created, edited, published and closed, but the\ndocument candidates actually read could only be attached in the web app.\n\nOwnership is checked BEFORE anything is written to storage, so a post you do\nnot own cannot leave an orphaned object behind. Talent-side organisations\nare refused - they apply to roles, they do not publish them.","operationId":"upload_job_post_jd_marketplace_job_posts__post_id__jd_post","parameters":[{"name":"post_id","in":"path","required":true,"schema":{"type":"string","description":"Job post id (UUID). Must be your org's.","title":"Post Id"},"description":"Job post id (UUID). Must be your org's."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_job_post_jd_marketplace_job_posts__post_id__jd_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/talent/{sdr_id}/messages":{"get":{"tags":["Marketplace"],"summary":"Get Talent Conversation","description":"Your org's thread with one candidate, OPENED IF IT DOES NOT EXIST YET.\n\nReturns `conversation_id`, the messages, and the candidate's display name -\ntheir codename, not their real name, while they are anonymous and you have\nnot hired them. Opening an empty thread notifies nobody.","operationId":"get_talent_conversation_marketplace_talent__sdr_id__messages_get","parameters":[{"name":"sdr_id","in":"path","required":true,"schema":{"type":"string","description":"Talent profile id (UUID).","title":"Sdr Id"},"description":"Talent profile id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"},"post":{"tags":["Marketplace"],"summary":"Send Talent Message","description":"Message a candidate as your org. REACHES A PERSON.\n\nRaises an in-app notification AND sends the candidate an email, on the spot,\nsigned with your org's name. The thread is opened if it does not exist.","operationId":"send_talent_message_marketplace_talent__sdr_id__messages_post","parameters":[{"name":"sdr_id","in":"path","required":true,"schema":{"type":"string","description":"Talent profile id (UUID).","title":"Sdr Id"},"description":"Talent profile id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MessageSendRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/me/messages":{"get":{"tags":["Marketplace"],"summary":"List My Conversations","description":"Your threads as TALENT, newest first, with each client's display name.\n\nAn agency account sees every thread across its roster, because it is the\ntalent side of all of them. A graph8 support thread is always present.\n404 when the key's principal has no marketplace profile.","operationId":"list_my_conversations_marketplace_me_messages_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/org/meetings":{"get":{"tags":["Marketplace"],"summary":"List Org Marketplace Meetings","description":"Meetings run by everyone your org has hired, with who ran each one.\n\nScoped to the key's own org; there is no parameter for it.","operationId":"list_org_marketplace_meetings_marketplace_org_meetings_get","parameters":[{"name":"sdr_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only this hire (talent profile id, UUID).","title":"Sdr Id"},"description":"Only this hire (talent profile id, UUID)."},{"name":"hiring_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only this contract (UUID).","title":"Hiring Id"},"description":"Only this contract (UUID)."},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"enum":["scheduled","taken","rescheduled","missed","cancelled"],"type":"string"},{"type":"null"}],"title":"Status"}},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"YYYY-MM-DD, inclusive.","title":"Start Date"},"description":"YYYY-MM-DD, inclusive."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"YYYY-MM-DD, inclusive.","title":"End Date"},"description":"YYYY-MM-DD, inclusive."},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Substring of contact name, email or notes.","title":"Search"},"description":"Substring of contact name, email or notes."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplaceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"}},"/marketplace/org/meetings/{meeting_id}":{"get":{"tags":["Marketplace"],"summary":"Get Org Marketplace Meeting","description":"One meeting. 404 unless one of your org's hires ran it.","operationId":"get_org_marketplace_meeting_marketplace_org_meetings__meeting_id__get","parameters":[{"name":"meeting_id","in":"path","required":true,"schema":{"type":"string","description":"Meeting id (UUID).","title":"Meeting Id"},"description":"Meeting id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"marketplace:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Marketplace"],"summary":"Update Org Marketplace Meeting","description":"Edit a meeting. `status: taken` MAKES IT BILLABLE.\n\nThat transition is what the per-meeting rate charges for, and it notifies\nthe talent; `taken_at` is stamped the first time only. Everything else here\nis bookkeeping. Sending no editable field is a 400.","operationId":"update_org_marketplace_meeting_marketplace_org_meetings__meeting_id__patch","parameters":[{"name":"meeting_id","in":"path","required":true,"schema":{"type":"string","description":"Meeting id (UUID).","title":"Meeting Id"},"description":"Meeting id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OrgMeetingUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/talent/{sdr_id}/match/refresh":{"post":{"tags":["Marketplace"],"summary":"Refresh Talent Match","description":"Recompute this candidate's match score against your org. Asynchronous.\n\nAnswers 202 with `status: generating` straight away; poll\n`GET /marketplace/talent/{sdr_id}/match` for the result.","operationId":"refresh_talent_match_marketplace_talent__sdr_id__match_refresh_post","parameters":[{"name":"sdr_id","in":"path","required":true,"schema":{"type":"string","description":"Talent profile id (UUID).","title":"Sdr Id"},"description":"Talent profile id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/talent/{sdr_id}/match/analyze":{"post":{"tags":["Marketplace"],"summary":"Analyze Talent Match","description":"Open a copilot chat session seeded with this candidate and your brief.\n\nReturns the new `session_id`. It only SEEDS the session - no model runs\nuntil someone sends in it. 400 when your org has no Studio brief yet.","operationId":"analyze_talent_match_marketplace_talent__sdr_id__match_analyze_post","parameters":[{"name":"sdr_id","in":"path","required":true,"schema":{"type":"string","description":"Talent profile id (UUID).","title":"Sdr Id"},"description":"Talent profile id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/marketplace/shortlist/export":{"post":{"tags":["Marketplace"],"summary":"Export Marketplace Shortlist","description":"Create a contacts list from a shortlist of candidates.\n\nOnly candidates you can already see by name are exported - anonymous talent\nyou have not hired, and inactive profiles, are skipped and counted. 422 when\nnone are exportable. Refused for talent accounts.","operationId":"export_marketplace_shortlist_marketplace_shortlist_export_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ShortlistExportRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MarketplacePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"marketplace:run","x-graph8-lifecycle":"active"}},"/agency/me":{"get":{"tags":["Agency"],"summary":"Get Agency Me","description":"Describe the agency credential: agency org + authorized client count.","operationId":"get_agency_me_agency_me_get","parameters":[{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/agency/clients":{"get":{"tags":["Agency"],"summary":"List Agency Clients","description":"List the client orgs this agency key may target via X-Target-Org-Id.\n\nEach entry's ``org_id`` is the value to pass in the ``X-Target-Org-Id``\nheader on any subsequent request to operate that client org.","operationId":"list_agency_clients_agency_clients_get","parameters":[{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_dict__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/me":{"get":{"tags":["Me"],"summary":"Describe Current Key","description":"Describe the API key making this call, and what it can reach.\n\nReturns the caller's OWN credential only. There is no disclosure boundary\ncrossed: the client already holds this key, and every field here is derived\nfrom it.","operationId":"describe_current_key_me_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-lifecycle":"active"}},"/usage":{"get":{"tags":["Usage"],"summary":"Get Usage","description":"Current credit balance for the authenticated org — total, held, available, and lifetime totals.","operationId":"get_usage_usage_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_UsageBalanceResponse_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"usage:read","x-graph8-lifecycle":"active"}},"/usage/transactions":{"get":{"tags":["Usage"],"summary":"List Usage Transactions","description":"Paginated credit-transaction ledger for the authenticated org (most recent first).\n\nSupports both page-number pagination (`page`/`limit`) and opaque cursor\npagination (`cursor`). When `cursor` is supplied it wins; the response always\nreturns `next_cursor` for forward iteration.","operationId":"list_usage_transactions_usage_transactions_get","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number (ignored when `cursor` is supplied)","default":1,"title":"Page"},"description":"Page number (ignored when `cursor` is supplied)"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Items per page","default":50,"title":"Limit"},"description":"Items per page"},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Opaque pagination cursor from a prior response's `next_cursor`. When supplied it takes precedence over `page`.","title":"Cursor"},"description":"Opaque pagination cursor from a prior response's `next_cursor`. When supplied it takes precedence over `page`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_UsageTransactionResponse__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"usage:read","x-graph8-lifecycle":"active"}},"/logs":{"get":{"tags":["Logs"],"summary":"List Request Logs","description":"Recent API requests for the authenticated org (most recent first).\n\nUseful for debugging an integration: see your last calls, their status codes,\nand the request_id to correlate with the X-Request-Id header. Best-effort —\nentries are retained briefly and may be absent if logging was unavailable.","operationId":"list_request_logs_logs_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Max entries to return (most recent first)","default":50,"title":"Limit"},"description":"Max entries to return (most recent first)"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_RequestLogEntry__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/campaign-visitors":{"get":{"tags":["Analytics"],"summary":"Get Campaign Visitors","description":"Campaign Visitors report for the authenticated org (analytics report a23).\n\nReturns, for the resolved window:\n\n  * **summary** — KPI tiles (page events, campaign clicks, unique contacts /\n    steps, identified visitors, and the encrypted/plaintext/unparseable\n    diagnostic split). Click counters are email-security-scanner filtered\n    (humans only) so they match the in-app report — raw scanner traffic\n    (Microsoft Defender / SafeLinks) is excluded.\n  * **top_campaign_steps** — per sequencer step: clicks, unique contacts, a\n    human-readable label, and send-side context (emails sent / with link).\n  * **link_engagement** — per clicked destination URL: human clicks, unique\n    contacts, the emails-with-link denominator, and CTR% (clamped 0–100).\n  * **top_contacts** — who clicked, with resolved name/email (PII; omit via\n    `include_contacts=false`).\n\nEnrichment (labels, email, send counts, CTR) is best-effort: a field is\n``null`` when it couldn't be resolved, never a fabricated zero. An org with\nno visitor-tracking pipeline returns an empty report with\n``summary.jitsu_wired = false``.\n\nAgency keys: pass ``X-Target-Org-Id`` to run the report for a specific client\norg within your authorized set.","operationId":"get_campaign_visitors_analytics_campaign_visitors_get","parameters":[{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"description":"Window start (inclusive), YYYY-MM-DD. If omitted, derived from `days`.","title":"Start Date"},"description":"Window start (inclusive), YYYY-MM-DD. If omitted, derived from `days`."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"description":"Window end (inclusive), YYYY-MM-DD. If omitted, today.","title":"End Date"},"description":"Window end (inclusive), YYYY-MM-DD. If omitted, today."},{"name":"days","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","maximum":365,"minimum":1},{"type":"null"}],"description":"Rolling 'last N days from today'. Ignored when start_date/end_date are supplied.","title":"Days"},"description":"Rolling 'last N days from today'. Ignored when start_date/end_date are supplied."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Row cap for the steps + contacts tables","default":50,"title":"Limit"},"description":"Row cap for the steps + contacts tables"},{"name":"include_contacts","in":"query","required":false,"schema":{"type":"boolean","description":"Include the Top contacts table (contact name + email — PII). Set false to omit it entirely for a privacy-lean response.","default":true,"title":"Include Contacts"},"description":"Include the Top contacts table (contact name + email — PII). Set false to omit it entirely for a privacy-lean response."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CampaignVisitorsReport_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/realtime":{"get":{"tags":["Web Analytics"],"summary":"Get Realtime","description":"Get real-time analytics: active users in last 5 and 30 minutes.\n\n**Refresh rate**: Poll every 10 seconds for real-time updates.\n**Cache TTL**: 10 seconds","operationId":"get_realtime_analytics_realtime_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/realtime/pages":{"get":{"tags":["Web Analytics"],"summary":"Get Realtime Pages","description":"Get active pages in real-time (last 5 minutes).","operationId":"get_realtime_pages_analytics_realtime_pages_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"description":"Number of pages to return","default":10,"title":"Limit"},"description":"Number of pages to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/realtime/locations":{"get":{"tags":["Web Analytics"],"summary":"Get Realtime Locations","description":"Get active locations in real-time (last 5 minutes).","operationId":"get_realtime_locations_analytics_realtime_locations_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":1},{"type":"null"}],"description":"Number of locations to return","title":"Limit"},"description":"Number of locations to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/realtime/sources":{"get":{"tags":["Web Analytics"],"summary":"Get Realtime Sources","description":"Get traffic sources in real-time (last 5 minutes).","operationId":"get_realtime_sources_analytics_realtime_sources_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"description":"Number of sources to return","default":10,"title":"Limit"},"description":"Number of sources to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/audience/overview":{"get":{"tags":["Web Analytics"],"summary":"Get Audience Overview","description":"Get audience overview: total users, new users, sessions, page views.\n\n**Typical use**: Dashboard header metrics.","operationId":"get_audience_overview_analytics_audience_overview_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/audience/trend":{"get":{"tags":["Web Analytics"],"summary":"Get Audience Trend","description":"Get daily audience trend for line charts.\n\nReturns date, users, new_users, page_views, sessions per day.","operationId":"get_audience_trend_analytics_audience_trend_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/audience/geo":{"get":{"tags":["Web Analytics"],"summary":"Get Geo Countries","description":"Get geographic distribution by country.","operationId":"get_geo_countries_analytics_audience_geo_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Number of countries to return","default":50,"title":"Limit"},"description":"Number of countries to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/audience/geo/cities":{"get":{"tags":["Web Analytics"],"summary":"Get Geo Cities","description":"Get geographic distribution by city.","operationId":"get_geo_cities_analytics_audience_geo_cities_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Number of cities to return","default":50,"title":"Limit"},"description":"Number of cities to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/audience/technology":{"get":{"tags":["Web Analytics"],"summary":"Get Technology Overview","description":"Get technology overview: browsers, OS, and devices combined.","operationId":"get_technology_overview_analytics_audience_technology_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/audience/behavior":{"get":{"tags":["Web Analytics"],"summary":"Get Audience Behavior","description":"Get new vs returning visitors breakdown.","operationId":"get_audience_behavior_analytics_audience_behavior_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/audience/languages":{"get":{"tags":["Web Analytics"],"summary":"Get Audience Languages","description":"Get visitor languages breakdown.","operationId":"get_audience_languages_analytics_audience_languages_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Number of languages to return","default":20,"title":"Limit"},"description":"Number of languages to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/audience/demographics":{"get":{"tags":["Web Analytics"],"summary":"Get Audience Demographics","description":"Get combined demographics: countries, cities, languages.\n\nAggregates geographic and language data for the demographics view.\nReturns top 10 entries for each category.","operationId":"get_audience_demographics_analytics_audience_demographics_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/acquisition/channels":{"get":{"tags":["Web Analytics"],"summary":"Get Acquisition Channels","description":"Get acquisition by channel grouping.\n\nChannels: Direct, Organic Search, Paid Search, Organic Social,\nPaid Social, Email, Referral, Display, Affiliates, Other.","operationId":"get_acquisition_channels_analytics_acquisition_channels_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/acquisition/channels/trend":{"get":{"tags":["Web Analytics"],"summary":"Get Acquisition Channels Trend","description":"Get daily channel breakdown for stacked area charts.","operationId":"get_acquisition_channels_trend_analytics_acquisition_channels_trend_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/acquisition/sources":{"get":{"tags":["Web Analytics"],"summary":"Get Acquisition Sources","description":"Get acquisition by source/medium combination.","operationId":"get_acquisition_sources_analytics_acquisition_sources_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Number of sources to return","default":50,"title":"Limit"},"description":"Number of sources to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/acquisition/campaigns":{"get":{"tags":["Web Analytics"],"summary":"Get Acquisition Campaigns","description":"Get UTM campaign performance.\n\n**Cache TTL**: 300 seconds (5 min) - campaigns change less frequently.","operationId":"get_acquisition_campaigns_analytics_acquisition_campaigns_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Number of campaigns to return","default":50,"title":"Limit"},"description":"Number of campaigns to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/acquisition/referrals":{"get":{"tags":["Web Analytics"],"summary":"Get Acquisition Referrals","description":"Get top referring domains.","operationId":"get_acquisition_referrals_analytics_acquisition_referrals_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Number of referrers to return","default":50,"title":"Limit"},"description":"Number of referrers to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/acquisition/social":{"get":{"tags":["Web Analytics"],"summary":"Get Acquisition Social","description":"Get acquisition from social networks.","operationId":"get_acquisition_social_analytics_acquisition_social_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/acquisition/search":{"get":{"tags":["Web Analytics"],"summary":"Get Acquisition Search","description":"Get acquisition from search engines.","operationId":"get_acquisition_search_analytics_acquisition_search_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/behavior/pages":{"get":{"tags":["Web Analytics"],"summary":"Get Top Pages","description":"Get top pages by views and unique visitors.","operationId":"get_top_pages_analytics_behavior_pages_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Number of pages to return","default":50,"title":"Limit"},"description":"Number of pages to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/behavior/page-metrics":{"get":{"tags":["Web Analytics"],"summary":"Get Page Metrics","description":"Single-page rollup (views/visitors/forms/bookings) — Studio Content Calendar overlay.\n\nThe path goes into a ClickHouse SQL literal (escaped in the query builder);\nthe strict charset check here is the boundary defense, mirroring\n``_parse_write_keys``.","operationId":"get_page_metrics_analytics_behavior_page_metrics_get","parameters":[{"name":"path","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":1000,"description":"Exact context_page_path to roll up","title":"Path"},"description":"Exact context_page_path to roll up"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/behavior/landing-pages":{"get":{"tags":["Web Analytics"],"summary":"Get Landing Pages","description":"Get top landing pages (entry pages).","operationId":"get_landing_pages_analytics_behavior_landing_pages_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Number of pages to return","default":50,"title":"Limit"},"description":"Number of pages to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/behavior/exit-pages":{"get":{"tags":["Web Analytics"],"summary":"Get Exit Pages","description":"Get top exit pages (last pages in sessions).","operationId":"get_exit_pages_analytics_behavior_exit_pages_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Number of pages to return","default":50,"title":"Limit"},"description":"Number of pages to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/behavior/events":{"get":{"tags":["Web Analytics"],"summary":"Get Events","description":"Get custom events summary (track events).","operationId":"get_events_analytics_behavior_events_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Number of events to return","default":50,"title":"Limit"},"description":"Number of events to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/conversions/goals":{"get":{"tags":["Web Analytics"],"summary":"Get Goals","description":"Get goal completions overview.\n\nGoals: Form Submissions, Meeting Booked, Signup, Purchase.\n**Cache TTL**: 300 seconds (5 min)","operationId":"get_goals_analytics_conversions_goals_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/conversions/goals/trend":{"get":{"tags":["Web Analytics"],"summary":"Get Goals Trend","description":"Get daily trend for goal completions.","operationId":"get_goals_trend_analytics_conversions_goals_trend_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/conversions/rate":{"get":{"tags":["Web Analytics"],"summary":"Get Conversion Rate","description":"Get overall visitor-to-conversion rate.","operationId":"get_conversion_rate_analytics_conversions_rate_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/conversions/forms":{"get":{"tags":["Web Analytics"],"summary":"Get Forms","description":"Get form submission analytics.","operationId":"get_forms_analytics_conversions_forms_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Number of forms to return","default":50,"title":"Limit"},"description":"Number of forms to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/conversions/forms/trend":{"get":{"tags":["Web Analytics"],"summary":"Get Forms Trend","description":"Get daily form submissions trend.","operationId":"get_forms_trend_analytics_conversions_forms_trend_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/conversions/forms/analysis":{"get":{"tags":["Web Analytics"],"summary":"Get Form Analysis","description":"Get detailed form analysis with conversion rates.","operationId":"get_form_analysis_analytics_conversions_forms_analysis_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Number of forms to return","default":20,"title":"Limit"},"description":"Number of forms to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/conversions/funnel":{"get":{"tags":["Web Analytics"],"summary":"Get Funnel","description":"Get funnel analysis.\n\nDefault funnel: Site Visitors → Viewed Form → Submitted Form → Booked Meeting","operationId":"get_funnel_analytics_conversions_funnel_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/engagement/overview":{"get":{"tags":["Web Analytics"],"summary":"Get Engagement Overview","description":"Get engagement quality overview with trend indicators.\n\nReturns:\n- **total_sessions**: Total session count\n- **avg_session_depth**: Average pages per session\n- **avg_time_minutes**: Average session duration in minutes\n- **bounce_rate**: Percentage of single-page sessions\n- **engaged_sessions**: Sessions with >1 page AND >30s duration\n- **engaged_pct**: Percentage of engaged sessions\n- **Trend indicators**: Period-over-period comparison for each metric\n\n**Typical use**: Marketing Intelligence dashboard - Engagement Quality card.","operationId":"get_engagement_overview_analytics_engagement_overview_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/engagement/trend":{"get":{"tags":["Web Analytics"],"summary":"Get Engagement Trend","description":"Get daily engagement trend for line charts.\n\nReturns daily breakdown of:\n- sessions\n- avg_session_depth\n- avg_time_minutes\n- bounce_rate\n- engaged_sessions","operationId":"get_engagement_trend_analytics_engagement_trend_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/engagement/depth-distribution":{"get":{"tags":["Web Analytics"],"summary":"Get Session Depth Distribution","description":"Get session depth distribution for histogram visualization.\n\nReturns buckets: 1 page, 2 pages, 3 pages, 4-5 pages, 6-10 pages, 10+ pages.","operationId":"get_session_depth_distribution_analytics_engagement_depth_distribution_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/engagement/time-distribution":{"get":{"tags":["Web Analytics"],"summary":"Get Time On Site Distribution","description":"Get time on site distribution for histogram visualization.\n\nReturns buckets: 0s (bounce), 1-30s, 30s-1m, 1-3m, 3-10m, 10m+.","operationId":"get_time_on_site_distribution_analytics_engagement_time_distribution_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/engagement/by-landing-page":{"get":{"tags":["Web Analytics"],"summary":"Get Engagement By Landing Page","description":"Get engagement metrics by landing page.\n\nShows which landing pages drive best engagement quality.\nOnly includes pages with at least 10 sessions.","operationId":"get_engagement_by_landing_page_analytics_engagement_by_landing_page_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Number of pages to return","default":20,"title":"Limit"},"description":"Number of pages to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/engagement/by-channel":{"get":{"tags":["Web Analytics"],"summary":"Get Engagement By Channel","description":"Get engagement metrics by acquisition channel.\n\nShows which channels drive best engagement quality.","operationId":"get_engagement_by_channel_analytics_engagement_by_channel_get","parameters":[{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/engagement/by-campaign":{"get":{"tags":["Web Analytics"],"summary":"Get Engagement By Campaign","description":"Get engagement metrics by UTM campaign.\n\nExtended campaign metrics including engagement quality.\n**Cache TTL**: 300 seconds (5 min) - campaigns change less frequently.","operationId":"get_engagement_by_campaign_analytics_engagement_by_campaign_get","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Number of campaigns to return","default":50,"title":"Limit"},"description":"Number of campaigns to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"date_from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to.","title":"Date From"},"description":"Anchored window start (YYYY-MM-DD). Must be sent with date_to."},{"name":"date_to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from.","title":"Date To"},"description":"Anchored window end (YYYY-MM-DD). Must be sent with date_from."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC).","title":"Start Date"},"description":"Alias of date_from (YYYY-MM-DD), the name the other analytics reports use. Sent alone, the window runs from start_date to today (UTC)."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date.","title":"End Date"},"description":"Alias of date_to (YYYY-MM-DD). Sent alone, the window is the `days` days ending on end_date."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/marketing/overview":{"get":{"tags":["Marketing Intelligence"],"summary":"Get Marketing Overview","description":"Get the Marketing Intelligence Overview (4-card dashboard).\n\n**PRD Reference:** FR-1 Marketing System Health\n\nReturns:\n- **qualified_traffic**: Identified visitors, identification rate, trend\n- **engagement_quality**: Session depth, time on site, bounce rate, trends\n- **campaign_influence**: Top campaign, influenced count, outbound conversion\n- **pipeline_impact**: Meetings booked, replies, outbound metrics, trends\n\n**Typical use**: Main Marketing Intelligence dashboard landing page.","operationId":"get_marketing_overview_analytics_marketing_overview_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/MarketingResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/marketing/outbound-bridge":{"get":{"tags":["Marketing Intelligence"],"summary":"Get Outbound Bridge Overview","description":"Get overview of web-to-outbound bridge performance.\n\n**PRD Reference:** FR-6 Outbound Bridge View\n\nReturns:\n- **web_visitors**: Total unique web visitors\n- **identified_visitors**: Visitors resolved to contacts\n- **added_to_outbound**: Contacts who received outbound emails\n- **total_replies**: Total email replies\n- **meetings_booked**: Total meetings from web visitors\n- **identification_rate**: % of visitors identified\n- **outbound_conversion_pct**: % of identified contacts added to outbound\n- **reply_rate**: % of outbound contacts who replied\n\nThis is the key differentiator: connecting web behavior to outbound outcomes.","operationId":"get_outbound_bridge_overview_analytics_marketing_outbound_bridge_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/MarketingResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/marketing/outbound-bridge/by-campaign":{"get":{"tags":["Marketing Intelligence"],"summary":"Get Outbound Bridge By Campaign","description":"Get web-to-outbound metrics by UTM campaign.\n\n**PRD Reference:** FR-2 Campaign Attribution + FR-6 Outbound Bridge\n\nShows the full attribution chain per campaign:\nCampaign -> Visitors -> Identified -> Engaged -> Outbound -> Replies -> Meetings","operationId":"get_outbound_bridge_by_campaign_analytics_marketing_outbound_bridge_by_campaign_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Number of campaigns to return","default":50,"title":"Limit"},"description":"Number of campaigns to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/MarketingResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/marketing/outbound-bridge/by-landing-page":{"get":{"tags":["Marketing Intelligence"],"summary":"Get Outbound Bridge By Landing Page","description":"Get web-to-outbound metrics by landing page.\n\nShows which entry pages drive best outbound outcomes.\nOnly includes pages with at least 10 visitors.","operationId":"get_outbound_bridge_by_landing_page_analytics_marketing_outbound_bridge_by_landing_page_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Number of pages to return","default":50,"title":"Limit"},"description":"Number of pages to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/MarketingResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/marketing/outbound-bridge/by-channel":{"get":{"tags":["Marketing Intelligence"],"summary":"Get Outbound Bridge By Channel","description":"Get web-to-outbound metrics by acquisition channel.\n\nShows which channels drive best outbound outcomes.\nChannels: Direct, Paid Search, Paid Social, Organic Search, Organic Social, etc.","operationId":"get_outbound_bridge_by_channel_analytics_marketing_outbound_bridge_by_channel_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/MarketingResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/marketing/outbound-bridge/trend":{"get":{"tags":["Marketing Intelligence"],"summary":"Get Outbound Bridge Trend","description":"Get daily trend of web-to-outbound bridge metrics.\n\nReturns daily breakdown of:\n- web_visitors\n- identified_visitors\n- added_to_outbound\n- replies\n- meetings\n\nNOTE: the outbound series (`added_to_outbound`, `replies`, `meetings`) stay\norg-wide when `write_key` is set — those events carry no site attribution.\nSee the SITE FILTER SCOPE block in `queries/outbound_bridge.py`.","operationId":"get_outbound_bridge_trend_analytics_marketing_outbound_bridge_trend_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/MarketingResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/marketing/outbound-bridge/top-sources":{"get":{"tags":["Marketing Intelligence"],"summary":"Get Top Performing Sources","description":"Get top performing web sources by outbound reply rate.\n\n**PRD Reference:** FR-6.3 Recommended Automations\n\nIdentifies the best sources for outbound engagement.\nOnly includes sources with at least 5 contacts added to outbound.\n\nUse this to identify which web behaviors predict outbound success.","operationId":"get_top_performing_sources_analytics_marketing_outbound_bridge_top_sources_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"description":"Number of sources to return","default":10,"title":"Limit"},"description":"Number of sources to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/MarketingResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/marketing/campaigns":{"get":{"tags":["Marketing Intelligence"],"summary":"Get Campaigns With Attribution","description":"Get campaign performance with full attribution chain.\n\n**PRD Reference:** FR-2 Campaign Attribution View\n\nReturns per campaign:\n- campaign_name, source, medium\n- visitors\n- engaged_pct (>1 page AND >30s)\n- identified_contacts\n- added_to_outbound\n- reply_rate\n- meetings_booked\n\n**Cache TTL**: 300 seconds (5 min)","operationId":"get_campaigns_with_attribution_analytics_marketing_campaigns_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Number of campaigns to return","default":50,"title":"Limit"},"description":"Number of campaigns to return"},{"name":"sort_by","in":"query","required":false,"schema":{"enum":["visitors","meetings_booked","reply_rate","engaged_pct"],"type":"string","description":"Sort by this metric (descending)","default":"visitors","title":"Sort By"},"description":"Sort by this metric (descending)"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/MarketingResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/marketing/content":{"get":{"tags":["Marketing Intelligence"],"summary":"Get Content With Attribution","description":"Get content performance with full attribution chain.\n\n**PRD Reference:** FR-4 Content Performance View\n\nReturns per page:\n- page_path, page_title\n- views\n- unique_visitors\n- identified_contacts\n- added_to_outbound\n- reply_rate\n- meetings_booked\n\nOnly includes pages with at least 10 unique visitors.","operationId":"get_content_with_attribution_analytics_marketing_content_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Number of pages to return","default":50,"title":"Limit"},"description":"Number of pages to return"},{"name":"sort_by","in":"query","required":false,"schema":{"enum":["views","meetings_booked","reply_rate","unique_visitors"],"type":"string","description":"Sort by this metric (descending)","default":"views","title":"Sort By"},"description":"Sort by this metric (descending)"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/MarketingResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/marketing/content/by-landing":{"get":{"tags":["Marketing Intelligence"],"summary":"Get Landing Pages With Attribution","description":"Get landing page performance with attribution metrics.\n\nSame as outbound-bridge/by-landing-page but with content context.\nShows which entry pages drive best business outcomes.","operationId":"get_landing_pages_with_attribution_analytics_marketing_content_by_landing_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Number of pages to return","default":50,"title":"Limit"},"description":"Number of pages to return"},{"name":"write_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated public keys to filter by","title":"Write Key"},"description":"Comma-separated public keys to filter by"},{"name":"include_bots","in":"query","required":false,"schema":{"type":"boolean","description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed.","default":false,"title":"Include Bots"},"description":"Count bot and crawler traffic too. Off by default: page views from self-identified crawlers, headless browsers, HTTP libraries and datacenter/cloud networks are excluded. Set true for the raw, unfiltered counts these reports returned before the filter existed."},{"name":"include_internal","in":"query","required":false,"schema":{"type":"boolean","description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded.","default":false,"title":"Include Internal"},"description":"Count internal traffic too. Off by default: page views on the graph8 app (app.graph8.com) and local development hosts, and browsers identified as your own team members (member emails and your company email domains), are excluded."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/MarketingResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/sdr/leaderboard":{"get":{"tags":["SDR Analytics"],"summary":"Get Sdr Leaderboard","description":"Get SDR leaderboard ranking all reps by activity.\n\nReturns a ranked list of SDRs with:\n- **emails_sent**: Total emails sent\n- **replies**: Total replies received\n- **reply_rate**: Reply rate percentage\n- **dials**: Total call dials\n- **connected**: Connected calls\n- **connect_rate**: Connect rate percentage\n- **meetings_booked**: Meetings scheduled\n- **activity_score**: Composite score (emails + dials*2 + meetings*10)\n\n**Cache TTL**: 60 seconds","operationId":"get_sdr_leaderboard_analytics_sdr_leaderboard_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"description":"Maximum SDRs to return","default":100,"title":"Limit"},"description":"Maximum SDRs to return"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SDRAnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/sdr/summary":{"get":{"tags":["SDR Analytics"],"summary":"Get Sdr Summary","description":"Get team-wide SDR summary with aggregate totals (human SDR activity only).\n\nReturns:\n- **active_sdrs**: Number of SDRs with activity\n- **total_emails_sent**: Total emails sent across team\n- **total_replies**: Total replies received\n- **total_meetings**: Total meetings booked\n- **avg_reply_rate**: Team average reply rate\n\nNote: Voice AI call metrics are available via /voice-ai/summary endpoint.\n\n**Cache TTL**: 60 seconds","operationId":"get_sdr_summary_analytics_sdr_summary_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SDRAnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/sdr/ai-agents/summary":{"get":{"tags":["SDR Analytics"],"summary":"Get Ai Agents Summary","description":"Get AI Agents summary with aggregate totals for all AI-powered activities.\n\nReturns org-wide AI metrics:\n- **total_ai_emails**: Total AI-generated emails sent\n- **total_ai_replies**: Total replies to AI emails\n- **total_ai_dials**: Total AI dialer calls initiated\n- **total_ai_connected**: Total AI calls that connected\n- **ai_connect_rate**: AI call connection rate percentage\n- **total_ai_meetings**: Total meetings booked by AI\n\n**Cache TTL**: 60 seconds","operationId":"get_ai_agents_summary_analytics_sdr_ai_agents_summary_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SDRAnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/sdr/trends":{"get":{"tags":["SDR Analytics"],"summary":"Get Sdr Trends","description":"Get SDR activity trends over time for charts.\n\nReturns time series data with:\n- **period**: Date or week start\n- **emails_sent**: Emails sent in period\n- **replies**: Replies in period\n- **dials**: Dials in period\n- **connected**: Connected calls in period\n- **meetings_booked**: Meetings in period\n- **reply_rate**: Period reply rate\n- **connect_rate**: Period connect rate\n\n**Cache TTL**: 60 seconds","operationId":"get_sdr_trends_analytics_sdr_trends_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"granularity","in":"query","required":false,"schema":{"enum":["day","week"],"type":"string","description":"Aggregation period: 'day' or 'week'","default":"day","title":"Granularity"},"description":"Aggregation period: 'day' or 'week'"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SDRAnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/sdr/{sdr_email}":{"get":{"tags":["SDR Analytics"],"summary":"Get Sdr Detail","description":"Get detailed breakdown for a specific SDR.\n\nReturns:\n- **sdr_email**: SDR email address\n- **totals**: Aggregate metrics for the period\n- **daily**: Day-by-day breakdown of activity\n\nUseful for SDR detail modal/drill-down view.\n\n**Cache TTL**: 60 seconds","operationId":"get_sdr_detail_analytics_sdr__sdr_email__get","parameters":[{"name":"sdr_email","in":"path","required":true,"schema":{"type":"string","description":"SDR email address","title":"Sdr Email"},"description":"SDR email address"},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SDRAnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/dialer/performance":{"get":{"tags":["Dialer Analytics"],"summary":"Get Dialer Performance","description":"Combined SDR dashboard data.\n\nReturns metrics for the given date range (defaults to today),\nyesterday (for trends), daily breakdown, disposition distribution,\npersonal bests, and current streak.\n\nPass `sdr_email` to view another SDR's performance (e.g. as a manager).\nPass `start_date`/`end_date` for a custom date range; personal bests and\nthe streak are then measured within that range too.","operationId":"get_dialer_performance_analytics_dialer_performance_get","parameters":[{"name":"sdr_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"SDR email to view. Defaults to current user.","title":"Sdr Email"},"description":"SDR email to view. Defaults to current user."},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Start date (YYYY-MM-DD). Defaults to today.","title":"Start Date"},"description":"Start date (YYYY-MM-DD). Defaults to today."},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"End date (YYYY-MM-DD). Defaults to today.","title":"End Date"},"description":"End date (YYYY-MM-DD). Defaults to today."},{"name":"tz","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Viewer's IANA timezone (e.g. Asia/Karachi). start_date/end_date and the daily buckets are read as calendar days in it. Omit for UTC days.","title":"Tz"},"description":"Viewer's IANA timezone (e.g. Asia/Karachi). start_date/end_date and the daily buckets are read as calendar days in it. Omit for UTC days."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DialerAnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/dialer/leaderboard":{"get":{"tags":["Dialer Analytics"],"summary":"Get Dialer Leaderboard","description":"Org-wide SDR leaderboard ranked by meetings booked.\n\nAccepts either explicit `start_date`/`end_date` or a `period` preset.\nIf neither is provided, defaults to today.","operationId":"get_dialer_leaderboard_analytics_dialer_leaderboard_get","parameters":[{"name":"period","in":"query","required":false,"schema":{"anyOf":[{"enum":["today","week","month"],"type":"string"},{"type":"null"}],"description":"Time period preset (fallback if no dates)","title":"Period"},"description":"Time period preset (fallback if no dates)"},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Start date (YYYY-MM-DD)","title":"Start Date"},"description":"Start date (YYYY-MM-DD)"},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"End date (YYYY-MM-DD)","title":"End Date"},"description":"End date (YYYY-MM-DD)"},{"name":"tz","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Viewer's IANA timezone (e.g. Asia/Karachi). start_date/end_date and the daily buckets are read as calendar days in it. Omit for UTC days.","title":"Tz"},"description":"Viewer's IANA timezone (e.g. Asia/Karachi). start_date/end_date and the daily buckets are read as calendar days in it. Omit for UTC days."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DialerAnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/dialer/quality":{"get":{"tags":["Dialer Analytics"],"summary":"Get Dialer Quality","description":"SDR quality scores from AI call grading.\n\nReturns average scores across 4 criteria (script adherence, objection\nhandling, value delivery, closing technique) and a daily quality trend.","operationId":"get_dialer_quality_analytics_dialer_quality_get","parameters":[{"name":"sdr_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"SDR email. Defaults to current user.","title":"Sdr Email"},"description":"SDR email. Defaults to current user."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Rolling window in days","default":30,"title":"Days"},"description":"Rolling window in days"},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Start date (YYYY-MM-DD)","title":"Start Date"},"description":"Start date (YYYY-MM-DD)"},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"End date (YYYY-MM-DD)","title":"End Date"},"description":"End date (YYYY-MM-DD)"},{"name":"tz","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Viewer's IANA timezone (e.g. Asia/Karachi). start_date/end_date and the daily buckets are read as calendar days in it. Omit for UTC days.","title":"Tz"},"description":"Viewer's IANA timezone (e.g. Asia/Karachi). start_date/end_date and the daily buckets are read as calendar days in it. Omit for UTC days."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DialerAnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/dialer/quality/leaderboard":{"get":{"tags":["Dialer Analytics"],"summary":"Get Quality Leaderboard","description":"Org-wide quality ranking from AI call grading.\n\nReturns average quality scores per SDR, ordered by overall score descending.\nUsed for the leaderboard quality column.","operationId":"get_quality_leaderboard_analytics_dialer_quality_leaderboard_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Rolling window in days","default":30,"title":"Days"},"description":"Rolling window in days"},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Start date (YYYY-MM-DD)","title":"Start Date"},"description":"Start date (YYYY-MM-DD)"},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"End date (YYYY-MM-DD)","title":"End Date"},"description":"End date (YYYY-MM-DD)"},{"name":"tz","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Viewer's IANA timezone (e.g. Asia/Karachi). start_date/end_date and the daily buckets are read as calendar days in it. Omit for UTC days.","title":"Tz"},"description":"Viewer's IANA timezone (e.g. Asia/Karachi). start_date/end_date and the daily buckets are read as calendar days in it. Omit for UTC days."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DialerAnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/dialer/leaderboard/sdr/{sdr_email}":{"get":{"tags":["Dialer Analytics"],"summary":"Get Sdr Dialer Detail","description":"Detailed daily breakdown for a specific SDR's dialer activity.","operationId":"get_sdr_dialer_detail_analytics_dialer_leaderboard_sdr__sdr_email__get","parameters":[{"name":"sdr_email","in":"path","required":true,"schema":{"type":"string","description":"SDR email address","title":"Sdr Email"},"description":"SDR email address"},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Number of days to analyze","default":30,"title":"Days"},"description":"Number of days to analyze"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DialerAnalyticsResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/dialer/grading/search":{"post":{"tags":["Dialer Analytics"],"summary":"Search Graded Calls","description":"Search and filter graded calls with full transcripts and AI evaluations.\n\nQueries the voice database directly for call results that have grading data.","operationId":"search_graded_calls_analytics_dialer_grading_search_post","parameters":[{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"description":"Page number","default":1,"title":"Page"},"description":"Page number"},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Results per page","default":20,"title":"Page Size"},"description":"Results per page"},{"name":"sdr_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by SDR email","title":"Sdr Email"},"description":"Filter by SDR email"},{"name":"campaign_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by campaign ID","title":"Campaign Id"},"description":"Filter by campaign ID"},{"name":"min_score","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","maximum":40,"minimum":0},{"type":"null"}],"description":"Minimum overall score","title":"Min Score"},"description":"Minimum overall score"},{"name":"max_score","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","maximum":40,"minimum":0},{"type":"null"}],"description":"Maximum overall score","title":"Max Score"},"description":"Maximum overall score"},{"name":"start_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Start date (YYYY-MM-DD)","title":"Start Date"},"description":"Start date (YYYY-MM-DD)"},{"name":"end_date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"End date (YYYY-MM-DD)","title":"End Date"},"description":"End date (YYYY-MM-DD)"},{"name":"sort_by","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Sort by: date or score","default":"date","title":"Sort By"},"description":"Sort by: date or score"},{"name":"sort_order","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Sort order: asc or desc","default":"desc","title":"Sort Order"},"description":"Sort order: asc or desc"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/org/sso":{"get":{"tags":["Settings"],"summary":"Get Sso Config","description":"The org's SSO configuration, or empty if none is set up.","operationId":"get_sso_config_org_sso_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Settings"],"summary":"Delete Sso Config","description":"Remove the SSO configuration entirely. NOT REVERSIBLE.\n\n`/deactivate` switches SSO off and keeps the configuration; this throws it\naway, and setting it up again means going back to the identity provider.","operationId":"delete_sso_config_org_sso_delete","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"account:delete","x-graph8-lifecycle":"active"}},"/org/sso/metadata":{"get":{"tags":["Settings"],"summary":"Get Sso Metadata","description":"Service-provider metadata to hand to the identity provider.\n\nThis is what you paste into Okta, Entra or similar when configuring the\nother side of the trust. It describes graph8; it contains no secret.","operationId":"get_sso_metadata_org_sso_metadata_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/org/sso/saml":{"put":{"tags":["Settings"],"summary":"Configure Saml Sso","description":"Configure SAML sign-in. Does NOT switch it on - see `/activate`.\n\nConfiguring and activating are separate calls in the app and stay separate\nhere, so a half-finished configuration cannot lock anyone out.","operationId":"configure_saml_sso_org_sso_saml_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SAMLConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/sso/oidc":{"put":{"tags":["Settings"],"summary":"Configure Oidc Sso","description":"Configure OIDC sign-in. Does NOT switch it on - see `/activate`.","operationId":"configure_oidc_sso_org_sso_oidc_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OIDCConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/sso/sync":{"post":{"tags":["Settings"],"summary":"Sync Sso Config","description":"Re-push the stored configuration to the identity provider.\n\nUse it when the two sides have drifted - it reconciles rather than changing\nwhat you configured.","operationId":"sync_sso_config_org_sso_sync_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/org/sso/activate":{"post":{"tags":["Settings"],"summary":"Activate Sso","description":"Switch SSO on for the org.\n\nCheck `/org/sso` first: activating a configuration the identity provider\nhas not accepted is how an org locks itself out. Reversible with\n`/deactivate`, which is why this is the lighter of the two.","operationId":"activate_sso_org_sso_activate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/sso/deactivate":{"post":{"tags":["Settings"],"summary":"Deactivate Sso","description":"Switch SSO off. THE CONFIGURATION IS KEPT.\n\nEveryone falls back to whatever sign-in they had before SSO. If your org\nhas no other sign-in method, this is the call that strands them - check\nbefore running it from a script.","operationId":"deactivate_sso_org_sso_deactivate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"account:delete","x-graph8-lifecycle":"active"}},"/org/sso/enforcement":{"put":{"tags":["Settings"],"summary":"Update Sso Enforcement","description":"Decide whether SSO is the ONLY way in.\n\nEnforcing it blocks every other sign-in method. That is the point of it,\nand it is also the single most effective way to lock an org out of its own\naccount - enforce only once you have signed in through SSO yourself.","operationId":"update_sso_enforcement_org_sso_enforcement_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SsoEnforcementRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"account:delete","x-graph8-lifecycle":"active"}},"/org/settings/cost":{"get":{"tags":["Settings"],"summary":"Get Cost Settings","description":"Labour cost per rep and the commission model the cost reports use. Admin only.","operationId":"get_cost_settings_org_settings_cost_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Settings"],"summary":"Update Cost Settings","description":"Replace the cost configuration. Employee keys are email addresses, lowercased.","operationId":"update_cost_settings_org_settings_cost_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OrgCostSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/settings/deliverability-protection":{"get":{"tags":["Settings"],"summary":"Get Deliverability Protection","description":"Which high-risk content categories are blocked, with a preview of each rule set.","operationId":"get_deliverability_protection_org_settings_deliverability_protection_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Settings"],"summary":"Update Deliverability Protection","description":"Switch the protection on or off, and choose the blocked categories.\n\nOrg-wide: it changes what every sequence may send. Turning it off removes a\nguard, not a feature, so it is audited under the key-holder's identity.","operationId":"update_deliverability_protection_org_settings_deliverability_protection_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OrgDeliverabilityProtectionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/settings/departments":{"get":{"tags":["Settings"],"summary":"Get Departments","description":"The org's department taxonomy, in display order.","operationId":"get_departments_org_settings_departments_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Settings"],"summary":"Update Departments","description":"Replace the department list. Slugs must be unique; an omitted entry is removed.","operationId":"update_departments_org_settings_departments_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OrgDepartmentsUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/settings/departments/seed-defaults":{"post":{"tags":["Settings"],"summary":"Seed Department Defaults","description":"FORCE-REPLACE the taxonomy with the five defaults. Custom departments are lost.\n\nTiered `destructive` for exactly that reason: nothing in the path says so.","operationId":"seed_department_defaults_org_settings_departments_seed_defaults_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"account:delete","x-graph8-lifecycle":"active"}},"/org/settings/outbound-tracking":{"get":{"tags":["Settings"],"summary":"Get Outbound Tracking","description":"Whether outbound links are UTM-tagged, and on which channels.","operationId":"get_outbound_tracking_org_settings_outbound_tracking_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Settings"],"summary":"Update Outbound Tracking","description":"Replace the outbound tracking configuration.","operationId":"update_outbound_tracking_org_settings_outbound_tracking_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OrgOutboundTrackingRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/knowledge-governance":{"get":{"tags":["Knowledge"],"summary":"List Knowledge Governance Queue","description":"What is waiting for review in Knowledge Governance.","operationId":"list_knowledge_governance_queue_knowledge_governance_get","parameters":[{"name":"queue","in":"query","required":false,"schema":{"type":"string","maxLength":32,"description":"Which governance queue to read.","default":"review","title":"Queue"},"description":"Which governance queue to read."},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":1024},{"type":"null"}],"description":"Opaque cursor from the previous page.","title":"Cursor"},"description":"Opaque cursor from the previous page."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/knowledge-ontology":{"get":{"tags":["Knowledge"],"summary":"Get Ontology Overview","description":"The org's ontology as it stands.","operationId":"get_ontology_overview_knowledge_ontology_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/knowledge-ontology/standard":{"get":{"tags":["Knowledge"],"summary":"Get Standard Ontology","description":"The standard ontology yours is compared against.","operationId":"get_standard_ontology_knowledge_ontology_standard_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/knowledge-ontology/deviations":{"get":{"tags":["Knowledge"],"summary":"Get Ontology Deviations","description":"Where your ontology differs from the standard.\n\nA deviation is not automatically wrong - it is where your business calls\nsomething by its own name. This is the read that tells you which is which.","operationId":"get_ontology_deviations_knowledge_ontology_deviations_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/knowledge-ontology/readiness":{"get":{"tags":["Knowledge"],"summary":"Get Ontology Readiness","description":"Whether the ontology is complete enough to rely on.","operationId":"get_ontology_readiness_knowledge_ontology_readiness_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/knowledge-ontology/{concept_id}":{"put":{"tags":["Knowledge"],"summary":"Upsert Ontology Concept","description":"Define or redefine one concept in the ontology.\n\nAn upsert: the same `concept_id` twice edits rather than duplicating, which\nmakes it safe to retry.","operationId":"upsert_ontology_concept_knowledge_ontology__concept_id__put","parameters":[{"name":"concept_id","in":"path","required":true,"schema":{"type":"string","minLength":1,"maxLength":255,"title":"Concept Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OntologyConceptRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/settings/scrape-config":{"get":{"tags":["Scraping"],"summary":"Get Scrape Config","description":"How the org scrapes: which pages, how deep, how often.","operationId":"get_scrape_config_settings_scrape_config_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Scraping"],"summary":"Update Scrape Config","description":"Change the scraping configuration. Only what you send is written.","operationId":"update_scrape_config_settings_scrape_config_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ScrapeConfigUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/settings/scrape-config/crawl":{"post":{"tags":["Scraping"],"summary":"Start Full Site Crawl","description":"Crawl a whole site. RUNS IN THE BACKGROUND and can take a long time.\n\nReturns a job id immediately; poll\n`GET /settings/scrape-config/crawl/status/{job_id}` for progress. A full\ncrawl fetches every reachable page, so point it at a site you own.","operationId":"start_full_site_crawl_settings_scrape_config_crawl_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StartCrawlRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/settings/scrape-config/crawl/status/{job_id}":{"get":{"tags":["Scraping"],"summary":"Get Crawl Status","description":"How far a site crawl has got.","operationId":"get_crawl_status_settings_scrape_config_crawl_status__job_id__get","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","description":"Crawl job id.","title":"Job Id"},"description":"Crawl job id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/scrape/adapters":{"get":{"tags":["Scraping"],"summary":"List Scrape Adapters","description":"Which scrapers are available, and what each is good for.","operationId":"list_scrape_adapters_scrape_adapters_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/scrape/requests":{"post":{"tags":["Scraping"],"summary":"Submit Scrape Request","description":"Ask for a scrape. Returns a job to poll.\n\nScraping fetches pages from a third party and can cost credits depending on\nthe adapter - check `GET /scrape/adapters` before running this in a loop.","operationId":"submit_scrape_request_scrape_requests_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SubmitScrapeRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"enrichment:run","x-graph8-lifecycle":"active"}},"/scrape/jobs/{job_id}":{"get":{"tags":["Scraping"],"summary":"Get Scrape Job","description":"One scrape job and its result.","operationId":"get_scrape_job_scrape_jobs__job_id__get","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","description":"Scrape job id.","title":"Job Id"},"description":"Scrape job id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/scrape/jobs/{job_id}/confirm":{"post":{"tags":["Scraping"],"summary":"Confirm Scrape Job","description":"Accept a scrape result, so what it found is kept.","operationId":"confirm_scrape_job_scrape_jobs__job_id__confirm_post","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","description":"Scrape job id.","title":"Job Id"},"description":"Scrape job id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/scrape/jobs/{job_id}/reject":{"post":{"tags":["Scraping"],"summary":"Reject Scrape Job","description":"Discard a scrape result. What it found is not kept.","operationId":"reject_scrape_job_scrape_jobs__job_id__reject_post","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","description":"Scrape job id.","title":"Job Id"},"description":"Scrape job id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SettingsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"enrichment:write","x-graph8-lifecycle":"active"}},"/scrape/jobs/{job_id}/export.csv":{"get":{"tags":["Scraping"],"summary":"Export Scrape Job Csv","description":"Download one scrape run's results as a CSV file.\n\nA FILE, not the JSON envelope - the same bytes the app's download button\nserves. Results live for 7 days after a run finishes; after that this is a\n404 naming the reason, never an empty file that reads like a run that found\nnothing.","operationId":"export_scrape_job_csv_scrape_jobs__job_id__export_csv_get","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","description":"Scrape job id.","title":"Job Id"},"description":"Scrape job id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"The run's rows as CSV.","content":{"text/csv":{}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"enrichment:read","x-graph8-lifecycle":"active"}},"/customer-success/companies/{company_id}/context":{"get":{"tags":["Customer success"],"summary":"Get Company Context","description":"Everything known about this client, in one read.\n\nThe assembled picture - contacts, activity, brief state, linked records -\nrather than a single table. Open-shaped, because what belongs in \"the\ncontext\" grows with the product and a dropped section would read as\n\"nothing there\".","operationId":"get_company_context_customer_success_companies__company_id__context_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/customer-success/companies/{company_id}/inbox":{"get":{"tags":["Customer success"],"summary":"Get Company Inbox","description":"Every conversation with anyone at this company, across channels.\n\nThe company-level view of the inbox: merged and ordered by date, rather\nthan one thread per contact.","operationId":"get_company_inbox_customer_success_companies__company_id__inbox_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/customer-success/contacts/{contact_id}/inbox":{"get":{"tags":["Customer success"],"summary":"Get Contact Inbox","description":"The same rollup, narrowed to ONE person at the company.","operationId":"get_contact_inbox_customer_success_contacts__contact_id__inbox_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"string","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/customer-success/companies/{company_id}/sync":{"post":{"tags":["Customer success"],"summary":"Trigger Company Sync","description":"Re-pull this client's context from the sources that feed it.\n\nReaches outside graph8 for the meeting and transcript sources, which is\nwhy it gates on `integrations:run` rather than plain write. Call it when the\ncontext looks stale; it is otherwise on a schedule.","operationId":"trigger_company_sync_customer_success_companies__company_id__sync_post","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/customer-success/companies/{company_id}/brief":{"get":{"tags":["Customer success"],"summary":"Get Brief","description":"The last brief written for this client. Reading it costs nothing.","operationId":"get_brief_customer_success_companies__company_id__brief_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/customer-success/companies/{company_id}/brief/synthesize":{"post":{"tags":["Customer success"],"summary":"Synthesize Brief","description":"Write a fresh brief from everything currently known about this client.\n\nTHIS RUNS A LARGE LANGUAGE MODEL and therefore spends credits - the\nhandler calls the model directly and converts its failures into 502s. It\nis classified `billable` by an explicit rule for that reason: as a plain\nwrite it would make \"spend model credits on every account we have\" the\nsame grant as \"rename a company\".\n\n502 when the model is unavailable, which is distinct from a 500: retry it.","operationId":"synthesize_brief_customer_success_companies__company_id__brief_synthesize_post","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"knowledge:run","x-graph8-lifecycle":"active"}},"/customer-success/companies/{company_id}/transcripts":{"get":{"tags":["Customer success"],"summary":"List Company Transcripts","description":"Call transcripts linked to this client. Archived ones are hidden by default.","operationId":"list_company_transcripts_customer_success_companies__company_id__transcripts_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"participant_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only calls this person was on.","title":"Participant Email"},"description":"Only calls this person was on."},{"name":"transcript_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by transcript kind.","title":"Transcript Type"},"description":"Filter by transcript kind."},{"name":"include_archived","in":"query","required":false,"schema":{"type":"boolean","description":"Include archived transcripts.","default":false,"title":"Include Archived"},"description":"Include archived transcripts."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/customer-success/companies/{company_id}/transcripts/{transcript_id}":{"get":{"tags":["Customer success"],"summary":"Get Transcript","description":"One transcript in full, with its participants.","operationId":"get_transcript_customer_success_companies__company_id__transcripts__transcript_id__get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"transcript_id","in":"path","required":true,"schema":{"type":"string","description":"Transcript id.","title":"Transcript Id"},"description":"Transcript id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/customer-success/companies/{company_id}/unlinked-transcripts":{"get":{"tags":["Customer success"],"summary":"List Unlinked Transcripts","description":"Transcripts that PROBABLY belong to this client but are not attached yet.\n\nThe candidate list for `PATCH /customer-success/transcripts/{id}/link`.\nAttaching one is what makes it show up in the brief and the context.","operationId":"list_unlinked_transcripts_customer_success_companies__company_id__unlinked_transcripts_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only transcripts from this date (YYYY-MM-DD).","title":"Date"},"description":"Only transcripts from this date (YYYY-MM-DD)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":20,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/customer-success/transcripts/{transcript_id}/archive":{"patch":{"tags":["Customer success"],"summary":"Archive Transcript","description":"Take a transcript out of the client's view.\n\nREVERSIBLE - `/unarchive` puts it back, and nothing is deleted. It is\nstill tiered `destructive`, because that is what the shared `/archive`\nrule derives for every archive route in the contract and an exception here\nwould make the tier mean two things.\n\nNo company gate on the route: this is addressed by transcript, not by\ncompany, so the caller's company scope is what authorises it - exactly as\nthe app has it.","operationId":"archive_transcript_customer_success_transcripts__transcript_id__archive_patch","parameters":[{"name":"transcript_id","in":"path","required":true,"schema":{"type":"string","description":"Transcript id.","title":"Transcript Id"},"description":"Transcript id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"companies:delete","x-graph8-lifecycle":"active"}},"/customer-success/transcripts/{transcript_id}/unarchive":{"patch":{"tags":["Customer success"],"summary":"Unarchive Transcript","description":"Put an archived transcript back in the client's view.","operationId":"unarchive_transcript_customer_success_transcripts__transcript_id__unarchive_patch","parameters":[{"name":"transcript_id","in":"path","required":true,"schema":{"type":"string","description":"Transcript id.","title":"Transcript Id"},"description":"Transcript id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/customer-success/transcripts/{transcript_id}/link":{"patch":{"tags":["Customer success"],"summary":"Link Transcript To Account","description":"Attach a transcript to an account.\n\nThis is what makes a call count: once linked, it feeds the context and the\nsynthesised brief. Candidates come from\n`/customer-success/companies/{id}/unlinked-transcripts`.","operationId":"link_transcript_to_account_customer_success_transcripts__transcript_id__link_patch","parameters":[{"name":"transcript_id","in":"path","required":true,"schema":{"type":"string","description":"Transcript id.","title":"Transcript Id"},"description":"Transcript id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CustomerSuccessTranscriptLinkRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/customer-success/companies/{company_id}/meetings":{"get":{"tags":["Customer success"],"summary":"List Company Meetings","description":"Calendar meetings with this client, and which transcript each one has.","operationId":"list_company_meetings_customer_success_companies__company_id__meetings_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/customer-success/meetings/{meeting_id}/link-transcript":{"patch":{"tags":["Customer success"],"summary":"Link Transcript To Meeting","description":"Say which transcript belongs to which meeting.\n\nDifferent from `/transcripts/{id}/link`: that one attaches a transcript to\nan ACCOUNT, this one attaches it to a specific calendar event. A\ntranscript can need both.","operationId":"link_transcript_to_meeting_customer_success_meetings__meeting_id__link_transcript_patch","parameters":[{"name":"meeting_id","in":"path","required":true,"schema":{"type":"string","description":"Calendar meeting id.","title":"Meeting Id"},"description":"Calendar meeting id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CustomerSuccessMeetingTranscriptLinkRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/customer-success/meetings/{meeting_id}/unlink-transcript":{"patch":{"tags":["Customer success"],"summary":"Unlink Transcript From Meeting","description":"Detach a transcript from a meeting. The transcript itself survives.","operationId":"unlink_transcript_from_meeting_customer_success_meetings__meeting_id__unlink_transcript_patch","parameters":[{"name":"meeting_id","in":"path","required":true,"schema":{"type":"string","description":"Calendar meeting id.","title":"Meeting Id"},"description":"Calendar meeting id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/customer-success/companies/{company_id}/drive-folder":{"post":{"tags":["Customer success"],"summary":"Connect Drive Folder","description":"Map a folder in the organisation's Google Drive to this client. OWNER/ADMIN.\n\nUses the Workspace connection the organisation already has - no new grant\nis made. Mapping the same Drive folder again UPDATES it, and mapping a\ndifferent folder to the same Library folder REPLACES that mapping. A sync\nis queued straight away so the files start importing. 400 when the\ncompany is not an active client.","operationId":"connect_drive_folder_customer_success_companies__company_id__drive_folder_post","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CustomerSuccessDriveFolderConnectRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"},"get":{"tags":["Customer success"],"summary":"Get Drive Folder","description":"The client's primary mapped folder, its first 50 files, and every mapping.\n\n`connected=false` when nothing is mapped. When Drive cannot be reached\nthe mapping is still returned, with `error` set and no files, rather\nthan failing the read.","operationId":"get_drive_folder_customer_success_companies__company_id__drive_folder_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"},"delete":{"tags":["Customer success"],"summary":"Disconnect Drive Folder","description":"Unmap Drive folders from this client. OWNER/ADMIN.\n\nWITH NO SELECTOR, EVERY MAPPING FOR THIS CLIENT IS REMOVED. With one or\nmore selectors, only the mappings matching all of them are removed. The\nfiles in Drive, and anything already imported, are left alone.","operationId":"disconnect_drive_folder_customer_success_companies__company_id__drive_folder_delete","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"folder_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Select the mapping by Google Drive folder id.","title":"Folder Id"},"description":"Select the mapping by Google Drive folder id."},{"name":"local_folder_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Select the mapping by Library folder key.","title":"Local Folder Key"},"description":"Select the mapping by Library folder key."},{"name":"library_folder_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Select the mapping by Library folder id.","title":"Library Folder Id"},"description":"Select the mapping by Library folder id."},{"name":"library_folder_path","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Select the mapping by Library folder path.","title":"Library Folder Path"},"description":"Select the mapping by Library folder path."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"companies:delete","x-graph8-lifecycle":"active"}},"/customer-success/companies/{company_id}/drive-folder-files":{"get":{"tags":["Customer success"],"summary":"Get Drive Folder Files","description":"Files (up to 200) in ONE mapped folder.\n\nPick the mapping with one selector, checked in this order: `folder_id`,\n`library_folder_id`, `library_folder_path`, `local_folder_key`. With none,\nthe primary mapping is used.","operationId":"get_drive_folder_files_customer_success_companies__company_id__drive_folder_files_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"folder_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Select the mapping by Google Drive folder id.","title":"Folder Id"},"description":"Select the mapping by Google Drive folder id."},{"name":"local_folder_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Select the mapping by Library folder key.","title":"Local Folder Key"},"description":"Select the mapping by Library folder key."},{"name":"library_folder_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Select the mapping by Library folder id.","title":"Library Folder Id"},"description":"Select the mapping by Library folder id."},{"name":"library_folder_path","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Select the mapping by Library folder path.","title":"Library Folder Path"},"description":"Select the mapping by Library folder path."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/team-members":{"get":{"tags":["Team members"],"summary":"List Team Members","description":"Everyone in the organisation's roster.\n\nOn the app's DIRECTORY router, not its admin one: this is what every deal\nowner and task assignee picker resolves names through, so it is gated on\n`settings:read` OR `team:read` rather than on administrator access.","operationId":"list_team_members_team_members_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by status.","title":"Status"},"description":"Filter by status."},{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by how the record was created: `propelauth`, `manual` or `clone`.","title":"Source"},"description":"Filter by how the record was created: `propelauth`, `manual` or `clone`."},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Match on name or email.","title":"Search"},"description":"Match on name or email."},{"name":"include_clones","in":"query","required":false,"schema":{"type":"boolean","description":"Include AI clone records.","default":false,"title":"Include Clones"},"description":"Include AI clone records."},{"name":"sync","in":"query","required":false,"schema":{"type":"boolean","description":"Pull the identity provider's membership list before answering. Slower, and it WRITES: it creates a member row for anyone in the organisation who has none yet.","default":false,"title":"Sync"},"description":"Pull the identity provider's membership list before answering. Slower, and it WRITES: it creates a member row for anyone in the organisation who has none yet."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"post":{"tags":["Team members"],"summary":"Create Team Member","description":"Add someone to the roster.\n\nThis creates a DIRECTORY record, not a login. It does not invite anyone,\ngrant any permission, or put them in the identity provider - a member\ncreated here can own a deal and be assigned a task, and cannot sign in.","operationId":"create_team_member_team_members_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MemberCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/team-members/sync":{"post":{"tags":["Team members"],"summary":"Sync Team Members","description":"Create a roster record for every org member who has none yet.\n\nReads the identity provider, so it gates on `team:run` rather than plain\nwrite. IDEMPOTENT: it only ever fills gaps, and the response says how many\nit created, so running it twice is a no-op rather than a duplicate.","operationId":"sync_team_members_team_members_sync_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"team:run","x-graph8-lifecycle":"active"}},"/team-members/me":{"get":{"tags":["Team members"],"summary":"Get My Team Member","description":"The roster record of the person who minted this key.\n\nAUTO-CREATES the record if that person has none yet, which is why an\norganisation-scoped key is refused here rather than being given a\nsynthetic identity to create a record for.","operationId":"get_my_team_member_team_members_me_get","parameters":[{"name":"include_preferences","in":"query","required":false,"schema":{"type":"boolean","description":"Include the member's preferences blob.","default":false,"title":"Include Preferences"},"description":"Include the member's preferences blob."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Team members"],"summary":"Update My Team Member","description":"Edit the key-holder's own roster record. Omitted fields are left alone.","operationId":"update_my_team_member_team_members_me_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MemberUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/team-members/me/enrich-linkedin":{"post":{"tags":["Team members"],"summary":"Enrich My Profile From Linkedin","description":"Fill the key-holder's own record from their LinkedIn profile.\n\nTHIS SPENDS ENRICHMENT CREDIT - it calls a paid provider - which is why it\ngates on `team:run` rather than plain write.\n\n`overwrite` defaults to false, so it fills EMPTY fields only. Turning it\non replaces values the person wrote themselves.","operationId":"enrich_my_profile_from_linkedin_team_members_me_enrich_linkedin_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MemberLinkedInEnrichRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"team:run","x-graph8-lifecycle":"active"}},"/team-members/me/import-social":{"post":{"tags":["Team members"],"summary":"Import My Social Profile","description":"Fill the key-holder's own record from a LinkedIn or Twitter profile.\n\nThe profile arrives in the body - nothing is fetched and no credit is\nspent. EMPTY fields are filled; values the person wrote are kept. Skills\nMERGE into expertise (capped at 15), up to three `recent_posts` are\nappended to the writing samples (ten kept), and a sent `job_history`\nREPLACES the stored one.","operationId":"import_my_social_profile_team_members_me_import_social_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MemberSocialImportRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/team-members/me/sync-desktop-profile":{"post":{"tags":["Team members"],"summary":"Sync My Desktop Profile","description":"Fill the key-holder's own record from a desktop-client profile record.\n\nThe shape is the graph8 Desktop app's local profile record. EMPTY fields\nonly - a value the person already has is never overwritten, including the\njob history. Skills and interests merge (capped at 15 each); education,\nfollower counts, recommendations and accomplishments land in the member's\npreferences blob.","operationId":"sync_my_desktop_profile_team_members_me_sync_desktop_profile_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MemberDesktopProfileSyncRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/team-members/{team_member_id}":{"get":{"tags":["Team members"],"summary":"Get Team Member","description":"One roster record. A directory read, not an administrative one.","operationId":"get_team_member_team_members__team_member_id__get","parameters":[{"name":"team_member_id","in":"path","required":true,"schema":{"type":"string","description":"Team member id.","title":"Team Member Id"},"description":"Team member id."},{"name":"include_preferences","in":"query","required":false,"schema":{"type":"boolean","description":"Include the member's preferences blob.","default":false,"title":"Include Preferences"},"description":"Include the member's preferences blob."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Team members"],"summary":"Update Team Member","description":"Edit somebody else's roster record. Omitted fields are left alone.","operationId":"update_team_member_team_members__team_member_id__patch","parameters":[{"name":"team_member_id","in":"path","required":true,"schema":{"type":"string","description":"Team member id.","title":"Team Member Id"},"description":"Team member id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MemberUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Team members"],"summary":"Delete Team Member","description":"Remove someone from the roster.\n\nThis does NOT remove them from the organisation or revoke their login -\nthat is a different decision and it is not published on this API. What it\ndoes remove is the row that deals and tasks point at as their owner.","operationId":"delete_team_member_team_members__team_member_id__delete","parameters":[{"name":"team_member_id","in":"path","required":true,"schema":{"type":"string","description":"Team member id.","title":"Team Member Id"},"description":"Team member id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"team:delete","x-graph8-lifecycle":"active"}},"/team-members/{team_member_id}/clone":{"post":{"tags":["Team members"],"summary":"Clone Team Member","description":"Create an AI clone of a member, carrying their voice and expertise.\n\nA NEW roster record, marked as a clone. The original is untouched, and the\nclone is excluded from the directory list unless `include_clones=true`.","operationId":"clone_team_member_team_members__team_member_id__clone_post","parameters":[{"name":"team_member_id","in":"path","required":true,"schema":{"type":"string","description":"Team member id.","title":"Team Member Id"},"description":"Team member id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MemberCloneRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/team-members/{team_member_id}/enrich-linkedin":{"post":{"tags":["Team members"],"summary":"Enrich Team Member From Linkedin","description":"Fill somebody else's record from their LinkedIn profile.\n\nTHIS SPENDS ENRICHMENT CREDIT. `overwrite` defaults to false, so it fills\nempty fields only.","operationId":"enrich_team_member_from_linkedin_team_members__team_member_id__enrich_linkedin_post","parameters":[{"name":"team_member_id","in":"path","required":true,"schema":{"type":"string","description":"Team member id.","title":"Team Member Id"},"description":"Team member id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MemberLinkedInEnrichRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"team:run","x-graph8-lifecycle":"active"}},"/team-members/{team_member_id}/generate-post":{"post":{"tags":["Team members"],"summary":"Generate Member Post","description":"Draft a social post in this member's voice.\n\nTHIS RUNS A MODEL and therefore spends credits, which is why it gates on\n`team:run`. It DRAFTS: nothing is posted anywhere.","operationId":"generate_member_post_team_members__team_member_id__generate_post_post","parameters":[{"name":"team_member_id","in":"path","required":true,"schema":{"type":"string","description":"Team member id.","title":"Team Member Id"},"description":"Team member id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"team:run","x-graph8-lifecycle":"active"}},"/team-members/{team_member_id}/notes":{"get":{"tags":["Team members"],"summary":"List Team Member Notes","description":"Internal notes colleagues keep on this person. Never customer-facing.","operationId":"list_team_member_notes_team_members__team_member_id__notes_get","parameters":[{"name":"team_member_id","in":"path","required":true,"schema":{"type":"string","description":"Team member id.","title":"Team Member Id"},"description":"Team member id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"},"post":{"tags":["Team members"],"summary":"Create Team Member Note","description":"Leave an internal note on a member.\n\nMENTIONING SOMEONE NOTIFIES THEM. Mentions carry an id, a name and\noptionally an email, and the note itself is org-internal.","operationId":"create_team_member_note_team_members__team_member_id__notes_post","parameters":[{"name":"team_member_id","in":"path","required":true,"schema":{"type":"string","description":"Team member id.","title":"Team Member Id"},"description":"Team member id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MemberNoteCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"}},"/team-members/{team_member_id}/notes/{note_id}":{"put":{"tags":["Team members"],"summary":"Update Team Member Note","description":"Rewrite a note. `content` REPLACES the whole body rather than appending.","operationId":"update_team_member_note_team_members__team_member_id__notes__note_id__put","parameters":[{"name":"team_member_id","in":"path","required":true,"schema":{"type":"string","description":"Team member id.","title":"Team Member Id"},"description":"Team member id."},{"name":"note_id","in":"path","required":true,"schema":{"type":"string","description":"Note id.","title":"Note Id"},"description":"Note id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MemberNoteUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"team:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Team members"],"summary":"Delete Team Member Note","description":"Delete a note.","operationId":"delete_team_member_note_team_members__team_member_id__notes__note_id__delete","parameters":[{"name":"team_member_id","in":"path","required":true,"schema":{"type":"string","description":"Team member id.","title":"Team Member Id"},"description":"Team member id."},{"name":"note_id","in":"path","required":true,"schema":{"type":"string","description":"Note id.","title":"Note Id"},"description":"Note id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"team:delete","x-graph8-lifecycle":"active"}},"/team-members/{team_member_id}/companies":{"get":{"tags":["Team members"],"summary":"Get Team Member Companies","description":"The companies this person owns.","operationId":"get_team_member_companies_team_members__team_member_id__companies_get","parameters":[{"name":"team_member_id","in":"path","required":true,"schema":{"type":"string","description":"Team member id.","title":"Team Member Id"},"description":"Team member id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/team-members/{team_member_id}/deals":{"get":{"tags":["Team members"],"summary":"Get Team Member Deals","description":"The deals this person owns. The quickest answer to \"what is on X's plate\".","operationId":"get_team_member_deals_team_members__team_member_id__deals_get","parameters":[{"name":"team_member_id","in":"path","required":true,"schema":{"type":"string","description":"Team member id.","title":"Team Member Id"},"description":"Team member id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/team-members/{team_member_id}/content":{"get":{"tags":["Team members"],"summary":"Get Team Member Content","description":"Content written in this person's voice, including anything drafted for them.","operationId":"get_team_member_content_team_members__team_member_id__content_get","parameters":[{"name":"team_member_id","in":"path","required":true,"schema":{"type":"string","description":"Team member id.","title":"Team Member Id"},"description":"Team member id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"team:read","x-graph8-lifecycle":"active"}},"/accounts/enriched":{"get":{"tags":["Accounts"],"summary":"List Accounts Enriched","description":"Accounts with their revenue and CRM overlays joined on.\n\nThe account-native read, and the one with no `/companies` twin: it joins\nthe canonical company record to `cb_accounts` (Stripe, MRR, churn) and to\nthe ABM overlay, coalescing the fields that appear on more than one of\nthem. Scoped to what the caller may see.","operationId":"list_accounts_enriched_accounts_enriched_get","parameters":[{"name":"skip","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Skip"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":10000,"minimum":1,"default":1000,"title":"Limit"}},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Match on company name or domain.","title":"Search"},"description":"Match on company name or domain."},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Lifecycle status, e.g. `trial` or `customer`.","title":"Status"},"description":"Lifecycle status, e.g. `trial` or `customer`."},{"name":"lifecycle_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter to one lifecycle stage.","title":"Lifecycle Id"},"description":"Filter to one lifecycle stage."},{"name":"website_status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter on website-check state.","title":"Website Status"},"description":"Filter on website-check state."},{"name":"in_pipeline","in":"query","required":false,"schema":{"type":"boolean","description":"Only accounts with an open deal.","default":false,"title":"In Pipeline"},"description":"Only accounts with an open deal."},{"name":"include_attribution","in":"query","required":false,"schema":{"type":"boolean","description":"Include first-touch attribution.","default":false,"title":"Include Attribution"},"description":"Include first-touch attribution."},{"name":"canonical_trial_cohort","in":"query","required":false,"schema":{"type":"boolean","description":"Use the same trial cohort `/accounts/trial-overview` uses, so the rows here and the counts there agree. Off by default, matching the app.","default":false,"title":"Canonical Trial Cohort"},"description":"Use the same trial cohort `/accounts/trial-overview` uses, so the rows here and the counts there agree. Off by default, matching the app."},{"name":"include_sessions","in":"query","required":false,"schema":{"type":"boolean","description":"Attach recent product-session links.","default":false,"title":"Include Sessions"},"description":"Attach recent product-session links."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/accounts/revenue-summary":{"get":{"tags":["Accounts"],"summary":"Get Revenue Summary","description":"How many accounts sit in each revenue bucket.\n\nUses the same status rule as `/accounts/enriched`, so the counts here and\nthe rows there always agree - which is the whole point of reading it.","operationId":"get_revenue_summary_accounts_revenue_summary_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/accounts/documents":{"get":{"tags":["Accounts"],"summary":"List Account Documents Batch","description":"Documents for MANY accounts in one call, grouped by account.\n\nAccount-native: it resolves ids across both the account and company id\nnamespaces and folds workflow steps into the result. Scoped - an id the\ncaller cannot see is dropped from the response rather than 403ing the\nwhole batch.","operationId":"list_account_documents_batch_accounts_documents_get","parameters":[{"name":"account_ids","in":"query","required":true,"schema":{"type":"string","description":"Comma-separated account ids. The batch ceiling is the app's own.","title":"Account Ids"},"description":"Comma-separated account ids. The batch ceiling is the app's own."},{"name":"folder","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only documents in this folder.","title":"Folder"},"description":"Only documents in this folder."},{"name":"include_content","in":"query","required":false,"schema":{"type":"boolean","description":"Include the full document bodies. Off by default because the payload grows by orders of magnitude when it is on.","default":false,"title":"Include Content"},"description":"Include the full document bodies. Off by default because the payload grows by orders of magnitude when it is on."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/accounts/intent-signal":{"get":{"tags":["Accounts"],"summary":"Get Intent Signal","description":"Organisation-wide buying intent, from your own website visitors.\n\nThe rollup behind the per-account `/accounts/{account_id}/intent-signals`.\nAn organisation with no visitor data yet gets an honest empty state rather\nthan zeros that read as \"nobody is interested\".","operationId":"get_intent_signal_accounts_intent_signal_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/accounts/trial-overview":{"get":{"tags":["Accounts"],"summary":"Get Trial Overview","description":"Headline trial numbers for your own organisation.\n\nCarries an honest `data_availability` map: a block whose source table is\nnot populated reports that it has no data rather than a misleading zero.\nRead it before treating any number here as a fact.\n\nAlways your own tenant. The app's cross-tenant `scope=platform` branch is\ngraph8-staff tooling and is not reachable through this API.","operationId":"get_trial_overview_accounts_trial_overview_get","parameters":[{"name":"view","in":"query","required":false,"schema":{"type":"string","pattern":"^(companies|contacts)$","description":"Count trials by company or by contact.","default":"companies","title":"View"},"description":"Count trials by company or by contact."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/accounts/trial-overview/list":{"get":{"tags":["Accounts"],"summary":"Get Trial Overview List","description":"The records behind one headline number.\n\nBuilt from the same predicates as the aggregate, so the list and the count\ncannot drift. When the source table is unpopulated it answers\n`data_available=false` with an empty list - again, not a misleading zero.","operationId":"get_trial_overview_list_accounts_trial_overview_list_get","parameters":[{"name":"metric","in":"query","required":false,"schema":{"type":"string","description":"Which headline number to drill into.","default":"","title":"Metric"},"description":"Which headline number to drill into."},{"name":"view","in":"query","required":false,"schema":{"type":"string","pattern":"^(companies|contacts)$","description":"Companies or contacts.","default":"companies","title":"View"},"description":"Companies or contacts."},{"name":"status","in":"query","required":false,"schema":{"type":"string","pattern":"^(active|expired)$","description":"Active or expired trials.","default":"active","title":"Status"},"description":"Active or expired trials."},{"name":"segment","in":"query","required":false,"schema":{"type":"string","description":"Enrichment segment, when `view=contacts`.","default":"all","title":"Segment"},"description":"Enrichment segment, when `view=contacts`."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/accounts/trial-dropoff-funnel":{"get":{"tags":["Accounts"],"summary":"Get Trial Dropoff Funnel","description":"Where trials stop, step by step.\n\nRate-limited per caller on its own budget, separately from the insight\nroute - it fans out across the org in Postgres and is the expensive read\non this surface.","operationId":"get_trial_dropoff_funnel_accounts_trial_dropoff_funnel_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Window, in days.","default":30,"title":"Days"},"description":"Window, in days."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/accounts/trial-dropoff-funnel/step":{"get":{"tags":["Accounts"],"summary":"Get Trial Dropoff Step","description":"Who fell out at one step of the funnel, and what they had done first.","operationId":"get_trial_dropoff_step_accounts_trial_dropoff_funnel_step_get","parameters":[{"name":"step_key","in":"query","required":true,"schema":{"type":"string","description":"The funnel step to drill into.","title":"Step Key"},"description":"The funnel step to drill into."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Window, in days.","default":30,"title":"Days"},"description":"Window, in days."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/trial-insight":{"post":{"tags":["Accounts"],"summary":"Get Trial Insight","description":"Why this trial is stalling, and the next thing to try.\n\nPOST only because it is rate-limited per caller and bounded work, NOT\nbecause it changes anything: it is rule-based, spends no credits, sends\nnothing and writes nothing. It is classified read-only for exactly that\nreason, so a read-only key can call it - which matters, because it is the\ndiagnosis you want before touching a customer.\n\n429 when the hourly budget is exhausted.","operationId":"get_trial_insight_accounts__account_id__trial_insight_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"Account id: the account UUID or the company id.","title":"Account Id"},"description":"Account id: the account UUID or the company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"companies:write","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/trial-journey":{"get":{"tags":["Accounts"],"summary":"Get Account Trial Journey","description":"What this account actually did during its trial, in order.","operationId":"get_account_trial_journey_accounts__account_id__trial_journey_get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"Account id: the account UUID or the company id.","title":"Account Id"},"description":"Account id: the account UUID or the company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/adoption-matrix":{"get":{"tags":["Accounts"],"summary":"Get Account Adoption Matrix","description":"Which parts of the product this account has taken up, and which it has not.\n\nOpen-shaped: the feature list grows with the product, and a dropped entry\nwould read as \"not adopted\" rather than \"not reported\".","operationId":"get_account_adoption_matrix_accounts__account_id__adoption_matrix_get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"Account id: the account UUID or the company id.","title":"Account Id"},"description":"Account id: the account UUID or the company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/intent-signals":{"get":{"tags":["Accounts"],"summary":"Get Account Intent Signals","description":"Buying-intent activity attributed to this account's domain.","operationId":"get_account_intent_signals_accounts__account_id__intent_signals_get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"Account id: the account UUID or the company id.","title":"Account Id"},"description":"Account id: the account UUID or the company id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"default":20,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/billing":{"get":{"tags":["Accounts"],"summary":"Get Account Billing","description":"What this account is paying: plan, next bill, and two years of invoices.\n\nReads the billing provider's synced rows - it never calls the provider and\nnever returns a provider credential. Missing billing data degrades to\nnulls and empty lists rather than a 404, so the shape is stable for an\naccount that has never been billed.","operationId":"get_account_billing_accounts__account_id__billing_get","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"Account id: the account UUID or the company id.","title":"Account Id"},"description":"Account id: the account UUID or the company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/stakeholders/{stakeholder_id}/generate-outreach":{"post":{"tags":["Accounts"],"summary":"Generate Stakeholder Outreach","description":"Draft one email, LinkedIn message or call script for one stakeholder.\n\nTHIS RUNS A LARGE LANGUAGE MODEL and spends credits, which is why it is\ntiered `billable`. It DRAFTS: nothing is sent. Grounded in the\norganisation's campaign brief and the stakeholder's own record; `warnings`\nsays what was missing. 404 when the account or stakeholder is not found.","operationId":"generate_stakeholder_outreach_accounts__account_id__stakeholders__stakeholder_id__generate_outreach_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"Account id: the account UUID or the company id.","title":"Account Id"},"description":"Account id: the account UUID or the company id."},{"name":"stakeholder_id","in":"path","required":true,"schema":{"type":"string","description":"The stakeholder (contact) to write for.","title":"Stakeholder Id"},"description":"The stakeholder (contact) to write for."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AccountStakeholderOutreachRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/accounts/{account_id}/generate-outreach-plan":{"post":{"tags":["Accounts"],"summary":"Generate Outreach Plan","description":"Draft a multi-touch outreach plan across every stakeholder on the account.\n\nTHIS RUNS A LARGE LANGUAGE MODEL and spends credits (`billable`). It is a\nPLAN - days, channels and message outlines - and nothing is scheduled or\nsent.","operationId":"generate_outreach_plan_accounts__account_id__generate_outreach_plan_post","parameters":[{"name":"account_id","in":"path","required":true,"schema":{"type":"string","description":"Account id: the account UUID or the company id.","title":"Account Id"},"description":"Account id: the account UUID or the company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/accounts/{mashup_company_id}/contacts":{"get":{"tags":["Accounts"],"summary":"Get Account Company Contacts","description":"The people at one TRIAL company - the account drawer's nested list.\n\nAccount-native: it answers only for a company that is a trial account in\nyour org, and is a 404 otherwise. `last_active` is always null (there is no\nper-contact product-usage join) and sparse fields are flagged in\n`data_availability`, so a blank reads as \"unknown\" rather than \"empty\".\n\nThe per-record company gate is re-declared on the route on the SAME\ninteger-id namespace the app's `verify_company_pk_access_dep` resolves.","operationId":"get_account_company_contacts_accounts__mashup_company_id__contacts_get","parameters":[{"name":"mashup_company_id","in":"path","required":true,"schema":{"type":"integer","description":"The company's integer id.","title":"Mashup Company Id"},"description":"The company's integer id."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"companies:read","x-graph8-lifecycle":"active"}},"/profile/mcp/tools":{"get":{"tags":["Profile"],"summary":"Get Available Mcp Tools","description":"The MCP tool groups and toolboxes a person can choose between.\n\n`groups[].value` and `toolboxes[].id` are the ids `PUT /profile/preferences`\naccepts as `mcp_tool_group`. The catalog is the same for every caller, so\nany key may read it.","operationId":"get_available_mcp_tools_profile_mcp_tools_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/profile/avatar":{"post":{"tags":["Profile"],"summary":"Upload Profile Avatar","description":"Set the key-holder's profile picture. Multipart, like the app.\n\nStored, then written to the identity provider. `synced_to_propelauth` is\nfalse when that second write failed: the picture is saved and the next\nidentity sync picks it up, so it is a soft warning rather than an error.\nA file of the wrong type or over 5 MB is a 400.","operationId":"upload_profile_avatar_profile_avatar_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_profile_avatar_profile_avatar_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/profile/preferences":{"get":{"tags":["Profile"],"summary":"Get Preferences","description":"The key-holder's own preferences: theme, locale, timezone, defaults.\n\nCreates an empty preferences row on first read rather than 404ing, which\nis the app's behaviour - so the shape is stable from the very first call.","operationId":"get_preferences_profile_preferences_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Profile"],"summary":"Update Preferences","description":"Update preferences. Omitted fields are LEFT ALONE, not cleared.\n\n`whatsapp_number` is validated against the messaging bridge before\nanything is written: claiming a number another person in the organisation\nalready registered is refused rather than silently stealing their route.","operationId":"update_preferences_profile_preferences_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProfilePreferencesUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/profile/notification-preferences":{"get":{"tags":["Profile"],"summary":"Get Notification Preferences","description":"Which events reach this person, and through which channel.\n\nOpen-shaped: the event catalogue and the delivery channels both grow with\nthe product, and a dropped entry would read as \"you are not subscribed\"\nrather than \"we did not tell you\".","operationId":"get_notification_preferences_profile_notification_preferences_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Profile"],"summary":"Update Notification Preference","description":"Update ONE event type, named by `event_type`.\n\nSingular on purpose, matching the app: a caller that sent the whole map\nwould race with the person changing a different toggle in the browser and\nsilently revert it.","operationId":"update_notification_preference_profile_notification_preferences_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProfileNotificationPreferenceUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/profile/deal-automations":{"get":{"tags":["Profile"],"summary":"Get Deal Automations","description":"What this person's calendar is allowed to do to their pipeline.\n\nPer pipeline: which meeting titles count, whether a scope of work is\nwritten, whether a quote is drafted, and whether the deal advances or\ncloses on its own.","operationId":"get_deal_automations_profile_deal_automations_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Profile"],"summary":"Update Deal Automations","description":"Configure the calendar-driven deal automations.\n\nRead `dry_run` before turning anything on: with it set, the automation\nreports what it WOULD do and creates nothing. `auto_close_deal_on_acceptance`\nis the one to be most careful with - it moves a deal to closed without a\nhuman in the loop.","operationId":"update_deal_automations_profile_deal_automations_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProfileDealAutomationsUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/profile/deal-automations/pipeline-hints":{"get":{"tags":["Profile"],"summary":"Get Pipeline Deal Hints","description":"Suggested settings per pipeline, derived from how it is actually used.\n\nAdvisory only - reading this changes nothing. It is what makes the\nconfiguration above a choice rather than a guess.","operationId":"get_pipeline_deal_hints_profile_deal_automations_pipeline_hints_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/profile/deal-automations/sync-now":{"post":{"tags":["Profile"],"summary":"Sync My Calendar Now","description":"Run the calendar sync immediately instead of waiting for the interval.\n\nReaches the key-holder's connected CALENDAR PROVIDER, so it gates on\n`integrations:run` rather than plain write. It can create deals and draft\nquotes as a consequence - whatever the configuration above allows - so it\nis worth calling once with `dry_run` on before relying on it.","operationId":"sync_my_calendar_now_profile_deal_automations_sync_now_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/profile/mcp/status":{"get":{"tags":["Profile"],"summary":"Get Mcp Connection Status","description":"Whether the key-holder has a live MCP connection, and when it was last used.","operationId":"get_mcp_connection_status_profile_mcp_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/profile/mcp/sessions":{"get":{"tags":["Profile"],"summary":"List Mcp Sessions","description":"The key-holder's active MCP sessions - one per connected client.","operationId":"list_mcp_sessions_profile_mcp_sessions_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/profile/mcp/sessions/{session_id}":{"delete":{"tags":["Profile"],"summary":"Revoke Mcp Session","description":"Disconnect one MCP client. It must re-authorise to connect again.\n\nOnly ever the key-holder's own session: the app matches the row on the\ncaller's user id, so another person's session id is a 404.","operationId":"revoke_mcp_session_profile_mcp_sessions__session_id__delete","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","description":"MCP session id, from `GET /profile/mcp/sessions`.","title":"Session Id"},"description":"MCP session id, from `GET /profile/mcp/sessions`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"account:delete","x-graph8-lifecycle":"active"}},"/profile/mcp/usage":{"get":{"tags":["Profile"],"summary":"Get Mcp Usage Stats","description":"How much the key-holder has used MCP: totals, this month, and the top tools.","operationId":"get_mcp_usage_stats_profile_mcp_usage_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/agency/reports/summary":{"get":{"tags":["Agency"],"summary":"Get Consolidated Summary","description":"Every client's numbers, added up. The agency top line.","operationId":"get_consolidated_summary_agency_reports_summary_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Trailing window, in days, ending today (UTC)."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/leaderboard":{"get":{"tags":["Agency"],"summary":"Get Agency Leaderboard","description":"Clients ranked against each other - best and worst performers.","operationId":"get_agency_leaderboard_agency_reports_leaderboard_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Trailing window, in days, ending today (UTC)."},{"name":"sort_by","in":"query","required":false,"schema":{"enum":["reply_rate","emails_sent","meetings_booked","connect_rate"],"type":"string","description":"Metric to rank on.","default":"reply_rate","title":"Sort By"},"description":"Metric to rank on."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Rows to return.","default":20,"title":"Limit"},"description":"Rows to return."},{"name":"meetings_channel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Count `meetings_booked` from ONE source channel instead of all of them. Changes what the ranking means, so set it deliberately.","title":"Meetings Channel"},"description":"Count `meetings_booked` from ONE source channel instead of all of them. Changes what the ranking means, so set it deliberately."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/comparison":{"get":{"tags":["Agency"],"summary":"Get Client Comparison","description":"Every client side by side on every metric, unranked.\n\nThe leaderboard sorts on ONE metric; this is the whole grid, for when the\nquestion is not \"who is top\" but \"who is different\".","operationId":"get_client_comparison_agency_reports_comparison_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Trailing window, in days, ending today (UTC)."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/trends":{"get":{"tags":["Agency"],"summary":"Get Agency Trends","description":"Activity across every client over time.","operationId":"get_agency_trends_agency_reports_trends_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Trailing window, in days, ending today (UTC)."},{"name":"granularity","in":"query","required":false,"schema":{"enum":["day","week"],"type":"string","description":"Bucket size.","default":"day","title":"Granularity"},"description":"Bucket size."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/health":{"get":{"tags":["Agency"],"summary":"Get Account Health","description":"A health score per client - which accounts need attention.\n\nThe report to poll if you only poll one: it is the agency's own churn\nearly-warning, and it is cached for five minutes rather than one.","operationId":"get_account_health_agency_reports_health_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Trailing window, in days, ending today (UTC)."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/deliverability":{"get":{"tags":["Agency"],"summary":"Get Cross Org Deliverability","description":"Sending health across every client, in one view.","operationId":"get_cross_org_deliverability_agency_reports_deliverability_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Trailing window, in days, ending today (UTC)."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/sdr-leaderboard":{"get":{"tags":["Agency"],"summary":"Get Agency Sdr Leaderboard","description":"Every rep at every client, ranked together.","operationId":"get_agency_sdr_leaderboard_agency_reports_sdr_leaderboard_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Trailing window, in days, ending today (UTC)."},{"name":"sort_by","in":"query","required":false,"schema":{"enum":["reply_rate","emails_sent","meetings_booked","activity_score","dials","connected","talk_time_minutes","grade_overall"],"type":"string","description":"Metric to rank on.","default":"reply_rate","title":"Sort By"},"description":"Metric to rank on."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Rows to return.","default":20,"title":"Limit"},"description":"Rows to return."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/sequence-leaderboard":{"get":{"tags":["Agency"],"summary":"Get Agency Sequence Leaderboard","description":"Every sequence at every client, ranked together.\n\nWhat an agency reuses a playbook on: the sequence that works at one client\nis the one to run at the next.","operationId":"get_agency_sequence_leaderboard_agency_reports_sequence_leaderboard_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Trailing window, in days, ending today (UTC)."},{"name":"sort_by","in":"query","required":false,"schema":{"enum":["reply_rate","contacted","meetings_booked","voice_ai_dials"],"type":"string","description":"Metric to rank on.","default":"reply_rate","title":"Sort By"},"description":"Metric to rank on."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Rows to return.","default":20,"title":"Limit"},"description":"Rows to return."},{"name":"org_filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it.","title":"Org Filter"},"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/clients/{org_id}":{"get":{"tags":["Agency"],"summary":"Get Client Detail","description":"One client's full metric set.","operationId":"get_client_detail_agency_reports_clients__org_id__get","parameters":[{"name":"org_id","in":"path","required":true,"schema":{"type":"string","description":"Client org id, from GET /agency/clients.","title":"Org Id"},"description":"Client org id, from GET /agency/clients."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Trailing window, in days, ending today (UTC)."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/clients/{org_id}/sequences":{"get":{"tags":["Agency"],"summary":"Get Client Sequences","description":"One client's live sequence states and their performance.","operationId":"get_client_sequences_agency_reports_clients__org_id__sequences_get","parameters":[{"name":"org_id","in":"path","required":true,"schema":{"type":"string","description":"Client org id.","title":"Org Id"},"description":"Client org id."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Trailing window, in days, ending today (UTC)."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/clients/{org_id}/deliverability":{"get":{"tags":["Agency"],"summary":"Get Client Deliverability","description":"One client's sending health.","operationId":"get_client_deliverability_agency_reports_clients__org_id__deliverability_get","parameters":[{"name":"org_id","in":"path","required":true,"schema":{"type":"string","description":"Client org id.","title":"Org Id"},"description":"Client org id."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Trailing window, in days, ending today (UTC)."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/meetings":{"get":{"tags":["Agency"],"summary":"Get Meetings Leaderboard","description":"Meetings per client, with cost per meeting.","operationId":"get_meetings_leaderboard_agency_reports_meetings_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Trailing window, in days, ending today (UTC)."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/meetings/by-channel":{"get":{"tags":["Agency"],"summary":"Get Meetings By Channel","description":"Which channel booked each meeting, across every client.","operationId":"get_meetings_by_channel_agency_reports_meetings_by_channel_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Trailing window, in days, ending today (UTC)."},{"name":"org_filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it.","title":"Org Filter"},"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/meetings/count":{"get":{"tags":["Agency"],"summary":"Get Meetings Count For Channel","description":"One channel's meeting count, across every client.\n\nThe cheap version of `/meetings/by-channel` when only one channel is\nwanted - it does not compute the rest.","operationId":"get_meetings_count_for_channel_agency_reports_meetings_count_get","parameters":[{"name":"channel","in":"query","required":true,"schema":{"type":"string","description":"The single channel to count.","title":"Channel"},"description":"The single channel to count."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Trailing window, in days, ending today (UTC)."},{"name":"org_filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it.","title":"Org Filter"},"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/dialer/leaderboard":{"get":{"tags":["Agency"],"summary":"Get Agency Dialer Leaderboard","description":"Every rep's dialling, across every client, ranked.","operationId":"get_agency_dialer_leaderboard_agency_reports_dialer_leaderboard_get","parameters":[{"name":"start_date","in":"query","required":true,"schema":{"type":"string","description":"Start date, `YYYY-MM-DD`.","title":"Start Date"},"description":"Start date, `YYYY-MM-DD`."},{"name":"end_date","in":"query","required":true,"schema":{"type":"string","description":"End date, `YYYY-MM-DD`.","title":"End Date"},"description":"End date, `YYYY-MM-DD`."},{"name":"sort_by","in":"query","required":false,"schema":{"enum":["dials","meetings_booked","connect_rate","talk_time_minutes","avg_quality_score"],"type":"string","description":"Metric to rank on.","default":"dials","title":"Sort By"},"description":"Metric to rank on."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Rows to return.","default":20,"title":"Limit"},"description":"Rows to return."},{"name":"org_filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it.","title":"Org Filter"},"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/dialer/quality-leaderboard":{"get":{"tags":["Agency"],"summary":"Get Agency Dialer Quality Leaderboard","description":"Call QUALITY scores, across every client - how calls went, not how many.","operationId":"get_agency_dialer_quality_leaderboard_agency_reports_dialer_quality_leaderboard_get","parameters":[{"name":"start_date","in":"query","required":true,"schema":{"type":"string","description":"Start date, `YYYY-MM-DD`.","title":"Start Date"},"description":"Start date, `YYYY-MM-DD`."},{"name":"end_date","in":"query","required":true,"schema":{"type":"string","description":"End date, `YYYY-MM-DD`.","title":"End Date"},"description":"End date, `YYYY-MM-DD`."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Rows to return.","default":20,"title":"Limit"},"description":"Rows to return."},{"name":"org_filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it.","title":"Org Filter"},"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/dialer/dashboard":{"get":{"tags":["Agency"],"summary":"Get Agency Dialer Dashboard","description":"Dialer KPIs aggregated over every client.","operationId":"get_agency_dialer_dashboard_agency_reports_dialer_dashboard_get","parameters":[{"name":"start_date","in":"query","required":true,"schema":{"type":"string","description":"Start date, `YYYY-MM-DD`.","title":"Start Date"},"description":"Start date, `YYYY-MM-DD`."},{"name":"end_date","in":"query","required":true,"schema":{"type":"string","description":"End date, `YYYY-MM-DD`.","title":"End Date"},"description":"End date, `YYYY-MM-DD`."},{"name":"org_filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it.","title":"Org Filter"},"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/dialer/grading/search":{"post":{"tags":["Agency"],"summary":"Search Agency Graded Calls","description":"Find graded calls across every client.\n\nA POST because the filter is a body, NOT because it writes - it reads, and\nit is tiered `read` for that reason rather than deriving `write` from the\nmethod. The body is an open dict here because it is an open dict in the\napp: the handler reads known keys off it with `.get` and ignores the rest,\nso mirroring it as a closed model would REJECT filters the app accepts.","operationId":"search_agency_graded_calls_agency_reports_dialer_grading_search_post","parameters":[{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Search filter. Recognised keys: `start_date`, `end_date`, `sdr_email`, `org_filter`, `min_score`, `max_score`, `sort_by` (default `date`), `page` (default 1), `page_size` (default 20). Anything else is ignored.","title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/voice-ai/dashboard":{"get":{"tags":["Agency"],"summary":"Get Voice Ai Dashboard","description":"Voice AI totals, per-client summary and daily trend.\n\nThe app calls this route `dashboard-v2`. An iteration number is an\ninternal fact about how the report was built, not something a customer\nshould have to type, so it is published as `dashboard` - there is no v1 in\nthis contract for it to be confused with.","operationId":"get_voice_ai_dashboard_agency_reports_voice_ai_dashboard_get","parameters":[{"name":"start_date","in":"query","required":true,"schema":{"type":"string","description":"Start date, `YYYY-MM-DD`.","title":"Start Date"},"description":"Start date, `YYYY-MM-DD`."},{"name":"end_date","in":"query","required":true,"schema":{"type":"string","description":"End date, `YYYY-MM-DD`.","title":"End Date"},"description":"End date, `YYYY-MM-DD`."},{"name":"org_filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it.","title":"Org Filter"},"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/voice-ai/agent-leaderboard":{"get":{"tags":["Agency"],"summary":"Get Voice Ai Agent Leaderboard","description":"Voice AI agents ranked across every client.","operationId":"get_voice_ai_agent_leaderboard_agency_reports_voice_ai_agent_leaderboard_get","parameters":[{"name":"start_date","in":"query","required":true,"schema":{"type":"string","description":"Start date, `YYYY-MM-DD`.","title":"Start Date"},"description":"Start date, `YYYY-MM-DD`."},{"name":"end_date","in":"query","required":true,"schema":{"type":"string","description":"End date, `YYYY-MM-DD`.","title":"End Date"},"description":"End date, `YYYY-MM-DD`."},{"name":"sort_by","in":"query","required":false,"schema":{"enum":["calls_initiated","calls_completed","completion_rate","voicemails_left"],"type":"string","description":"Metric to rank on.","default":"calls_initiated","title":"Sort By"},"description":"Metric to rank on."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Rows to return.","default":20,"title":"Limit"},"description":"Rows to return."},{"name":"org_filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it.","title":"Org Filter"},"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/voice-ai/quality-leaderboard":{"get":{"tags":["Agency"],"summary":"Get Voice Ai Quality Leaderboard","description":"Voice AI agents ranked on call QUALITY rather than volume.","operationId":"get_voice_ai_quality_leaderboard_agency_reports_voice_ai_quality_leaderboard_get","parameters":[{"name":"start_date","in":"query","required":true,"schema":{"type":"string","description":"Start date, `YYYY-MM-DD`.","title":"Start Date"},"description":"Start date, `YYYY-MM-DD`."},{"name":"end_date","in":"query","required":true,"schema":{"type":"string","description":"End date, `YYYY-MM-DD`.","title":"End Date"},"description":"End date, `YYYY-MM-DD`."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Rows to return.","default":20,"title":"Limit"},"description":"Rows to return."},{"name":"org_filter","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it.","title":"Org Filter"},"description":"Narrow to ONE client org. Silently ignored when it names an org outside this agency's authorized set - it can select within the set, never widen it."},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/agency/reports/voice-ai/grading/search":{"post":{"tags":["Agency"],"summary":"Search Voice Ai Graded Calls","description":"Find graded Voice AI calls across every client. Reads; does not write.","operationId":"search_voice_ai_graded_calls_agency_reports_voice_ai_grading_search_post","parameters":[{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Search filter. Recognised keys: `start_date`, `end_date`, `agent_name`, `org_filter`, `min_score`, `max_score`, `sort_by` (default `date`), `page` (default 1), `page_size` (default 25). Anything else is ignored.","title":"Body"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/usage/holds":{"get":{"tags":["Usage"],"summary":"Get Credit Holds","description":"Credits currently RESERVED against work in flight.\n\nThis is the difference `GET /usage` reports but cannot explain: a hold\nsubtracts from `available_credits` without appearing in the transaction\nledger, because nothing has been spent yet. An operation that reserves\ncredits up front and settles later shows up here in between.\n\nA balance that looks lower than the ledger says is almost always this.\n\nThe org is the authenticated key's own. There is no customer parameter on\nthis route.","operationId":"get_credit_holds_usage_holds_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/usage/subscription":{"get":{"tags":["Usage"],"summary":"Get Subscription Status","description":"Whether this organisation's subscription is active.\n\nWorth checking before anything that spends: a charge against an inactive\nsubscription is refused even when the balance is healthy, so \"insufficient\ncredits\" is not the only way spending fails.\n\n`raise_on_unavailable` is set, which is the whole point of answering this\nas its own route rather than as a boolean somewhere else: without it an\nunreachable billing service and an authoritatively-inactive subscription\nboth answer `false`, and those two mean opposite things. Unreachable\nbecomes a 503 here; `false` means false.","operationId":"get_subscription_status_usage_subscription_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/usage/pricing/llm":{"get":{"tags":["Usage"],"summary":"Get Llm Pricing","description":"What an LLM operation of this size would cost. Charges nothing.\n\nREAD `capped` before reading `credits`. Several tiers have a per-operation\nceiling, and for typical prompt sizes the ceiling is what is actually paid\n- so `credits` stops moving when the prompt grows, and\n`uncapped_credits` is what the token arithmetic alone would have produced.\nA caller that shows `credits` without `capped` gets asked why shortening\nthe prompt changed nothing.\n\n`found` is false for a tier that does not exist or is not currently\nactive; `credits` is then 0, which is not a price.","operationId":"get_llm_pricing_usage_pricing_llm_get","parameters":[{"name":"llm_tier","in":"query","required":true,"schema":{"type":"string","description":"Pricing tier, e.g. `g8_t1`. The same value that appears in the `llm_tier` column of `GET /usage/transactions`, which is where to find the tier a given operation actually bills at.","title":"Llm Tier"},"description":"Pricing tier, e.g. `g8_t1`. The same value that appears in the `llm_tier` column of `GET /usage/transactions`, which is where to find the tier a given operation actually bills at."},{"name":"input_tokens","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Prompt tokens.","default":0,"title":"Input Tokens"},"description":"Prompt tokens."},{"name":"output_tokens","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Completion tokens.","default":0,"title":"Output Tokens"},"description":"Completion tokens."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/usage/pricing/domains/{tld}":{"get":{"tags":["Usage"],"summary":"Get Domain Pricing","description":"What registering a domain on this TLD costs in credits.\n\nThe price `POST /channels/domains/purchase` will charge. A TLD with no\npricing row is a 404 rather than a zero - a missing price is not a free\ndomain.","operationId":"get_domain_pricing_usage_pricing_domains__tld__get","parameters":[{"name":"tld","in":"path","required":true,"schema":{"type":"string","description":"Top-level domain, with or without the leading dot - `com` and `.com` both resolve.","title":"Tld"},"description":"Top-level domain, with or without the leading dot - `com` and `.com` both resolve."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/usage/organization":{"get":{"tags":["Usage"],"summary":"Get Organization Usage","description":"This organization's credit usage over the last 7, 30 or 90 days, with the previous period for comparison.\n\n`range`, `totals` (credits used, operations, active days, busiest day), `previous` (with `change_pct`, null when\nthe previous period recorded nothing), a daily `series`, and a `breakdown` by service. `has_credit_account` is false\nwhen the organization has no credit account yet, which is not the same as \"no activity\". 504 when the aggregation\nis slow (retry), 500 when it fails.","operationId":"get_organization_usage_usage_organization_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","description":"Window length: 7, 30 or 90 days. Anything else is a 400.","default":30,"title":"Days"},"description":"Window length: 7, 30 or 90 days. Anything else is a 400."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/usage/pricing/services":{"get":{"tags":["Usage"],"summary":"List Service Pricing","description":"The credit rate of every service graph8 charges for, as published to customers.\n\nThe same list for every organization. A rate is what one unit of the service costs; what a particular operation\ncosts is on its own route (for an LLM call, `GET /usage/pricing/llm`).","operationId":"list_service_pricing_usage_pricing_services_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/usage/pricing/llm-tiers":{"get":{"tags":["Usage"],"summary":"List Llm Tier Pricing","description":"Every active AI usage tier and its published rates.\n\nPick a tier's name from here to price a specific call with `GET /usage/pricing/llm?llm_tier=`.","operationId":"list_llm_tier_pricing_usage_pricing_llm_tiers_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/usage/pricing/domains":{"get":{"tags":["Usage"],"summary":"List Domain Pricing","description":"Every active domain TLD and what registering one costs in credits.\n\nOne TLD is `GET /usage/pricing/domains/{tld}`.","operationId":"list_domain_pricing_usage_pricing_domains_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/billing":{"get":{"tags":["Usage"],"summary":"Get Company Billing","description":"What ONE of your customers is paying you: subscription, invoices,\nupcoming charge.\n\nRead from the `stripe_*` tables that the per-org Stripe sync populates\nfrom the customer's OWN connected account, so this is revenue the caller\nreceives - not what the caller owes graph8, which is `GET /usage`.\n\n`payment_method` is null by design rather than by omission: card data is\nnot synced, and the hosted portal is the only place it exists.\n\nA company in another org is a 404, not a 403 - the app's own choice, so\nthat the API cannot be used to test whether a company id exists somewhere\nelse.","operationId":"get_company_billing_companies__company_id__billing_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"integer","title":"Company Id"}},{"name":"invoice_limit","in":"query","required":false,"schema":{"type":"integer","maximum":50,"minimum":1,"description":"Invoices to return, newest first. 50 is a hard ceiling in the app, applied whatever is sent - declared honestly here so an over-large value is a 422 rather than a silently smaller answer.","default":20,"title":"Invoice Limit"},"description":"Invoices to return, newest first. 50 is a hard ceiling in the app, applied whatever is sent - declared honestly here so an over-large value is a 422 rather than a silently smaller answer."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/billing/products":{"get":{"tags":["Usage"],"summary":"List Billing Products","description":"The plans and credit packs graph8 sells, with their prices.\n\nThe same catalogue the Billing page renders. It is not per-organisation -\nevery caller sees the same list - which is why this is one of the very few\ncredit-server reads that can be published without a customer parameter.","operationId":"list_billing_products_billing_products_get","parameters":[{"name":"active_only","in":"query","required":false,"schema":{"type":"boolean","description":"Only products currently on sale.","default":true,"title":"Active Only"},"description":"Only products currently on sale."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/billing/products/{product_id}":{"get":{"tags":["Usage"],"summary":"Get Billing Product","description":"One plan or credit pack from the catalogue.","operationId":"get_billing_product_billing_products__product_id__get","parameters":[{"name":"product_id","in":"path","required":true,"schema":{"type":"string","description":"Product id from `GET /billing/products`.","title":"Product Id"},"description":"Product id from `GET /billing/products`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/summary":{"get":{"tags":["Analytics"],"summary":"Get Outbound Summary","description":"Email, calls and meetings in one call - the top-line outbound KPIs.\n\nThe cheapest way to ask \"how is outbound doing\": one request instead of\nthe three channel summaries below.","operationId":"get_outbound_summary_analytics_outbound_summary_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/email-metrics":{"get":{"tags":["Analytics"],"summary":"Get Email Metrics","description":"Sent, bounced, delivered, replied, and the rates between them.","operationId":"get_email_metrics_analytics_outbound_email_metrics_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/email-metrics/trend":{"get":{"tags":["Analytics"],"summary":"Get Email Trend","description":"The same email metrics, one row per day.","operationId":"get_email_trend_analytics_outbound_email_metrics_trend_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/email-metrics/by-sequence":{"get":{"tags":["Analytics"],"summary":"Get Email By Sequence","description":"Email metrics split by sequence - which campaign is carrying the org.","operationId":"get_email_by_sequence_analytics_outbound_email_metrics_by_sequence_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Sequences to return.","default":50,"title":"Limit"},"description":"Sequences to return."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/email-metrics/by-step":{"get":{"tags":["Analytics"],"summary":"Get Email By Step","description":"Email metrics by STEP ORDER - where in the sequence people drop.\n\nThe step view is the one that changes a sequence: a reply rate that dies\nat step three is a step-three problem, not a sequence problem.","operationId":"get_email_by_step_analytics_outbound_email_metrics_by_step_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"sequence_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to one sequence. Omit for every sequence's steps folded together by step order.","title":"Sequence Id"},"description":"Narrow to one sequence. Omit for every sequence's steps folded together by step order."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/call-metrics":{"get":{"tags":["Analytics"],"summary":"Get Call Metrics","description":"Dispatched, connected, completed, voicemail - call volume and outcome.","operationId":"get_call_metrics_analytics_outbound_call_metrics_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/call-metrics/trend":{"get":{"tags":["Analytics"],"summary":"Get Call Trend","description":"The same call metrics, one row per day.","operationId":"get_call_trend_analytics_outbound_call_metrics_trend_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/call-metrics/voice-ai":{"get":{"tags":["Analytics"],"summary":"Get Voice Ai Outcomes","description":"How the AI-placed calls ended, broken down by outcome.\n\nVoice AI only - the human dialer's own quality surface is\n`GET /analytics/dialer/*`, which already ships.","operationId":"get_voice_ai_outcomes_analytics_outbound_call_metrics_voice_ai_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/meeting-funnel":{"get":{"tags":["Analytics"],"summary":"Get Meeting Funnel","description":"Booked, held, cancelled - and the conversion between them.\n\nThe funnel, not the counts: `/meeting-metrics` answers how many, this\nanswers how many SURVIVED.","operationId":"get_meeting_funnel_analytics_outbound_meeting_funnel_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/meeting-metrics":{"get":{"tags":["Analytics"],"summary":"Get Meeting Metrics","description":"Meetings booked, cancelled, net, and the cancellation rate.","operationId":"get_meeting_metrics_analytics_outbound_meeting_metrics_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/meeting-metrics/trend":{"get":{"tags":["Analytics"],"summary":"Get Meeting Trend","description":"The same meeting metrics, one row per day.","operationId":"get_meeting_trend_analytics_outbound_meeting_metrics_trend_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/meeting-metrics/by-channel":{"get":{"tags":["Analytics"],"summary":"Get Meeting By Channel","description":"Which channel produced each booking - email, phone, or inbound.","operationId":"get_meeting_by_channel_analytics_outbound_meeting_metrics_by_channel_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/sequence-performance":{"get":{"tags":["Analytics"],"summary":"Get Sequence Performance","description":"Contacts to replies to meetings, one row per sequence.\n\nThe end-to-end view `/email-metrics/by-sequence` cannot give: that one\nstops at the reply, this one carries through to the meeting.","operationId":"get_sequence_performance_analytics_outbound_sequence_performance_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"description":"Sequences to return.","default":50,"title":"Limit"},"description":"Sequences to return."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/sequence-performance/{sequence_id}":{"get":{"tags":["Analytics"],"summary":"Get Sequence Performance By Id","description":"The same row for ONE sequence, without paging the list to find it.","operationId":"get_sequence_performance_by_id_analytics_outbound_sequence_performance__sequence_id__get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/channel-attribution":{"get":{"tags":["Analytics"],"summary":"Get Channel Attribution","description":"What each channel contributed - email versus phone versus LinkedIn.","operationId":"get_channel_attribution_analytics_outbound_channel_attribution_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/sdr-activity":{"get":{"tags":["Analytics"],"summary":"Get Sdr Activity","description":"Activity per rep across the window - the roster view.","operationId":"get_sdr_activity_analytics_outbound_sdr_activity_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/sdr-activity/leaderboard":{"get":{"tags":["Analytics"],"summary":"Get Sdr Leaderboard","description":"Reps ranked by reply rate.\n\nA rep is only ranked once they have sent at least ten emails - the app's\nown floor, and the reason a rep who sent three and got one reply does not\nappear at 33%.\n\nNot the same report as `GET /analytics/sdr/leaderboard`, which already\nships: that one ranks on the SDR analytics service's own activity roll-up,\nthis one on outbound sequence performance. Different services, different\nnumbers, both intentional.","operationId":"get_sdr_leaderboard_analytics_outbound_sdr_activity_leaderboard_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Reps to return.","default":20,"title":"Limit"},"description":"Reps to return."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/sdr-activity/daily":{"get":{"tags":["Analytics"],"summary":"Get Sdr Daily","description":"Per-rep activity broken out by day.","operationId":"get_sdr_daily_analytics_outbound_sdr_activity_daily_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"sdr_email","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to one rep. Omit for the whole team.","title":"Sdr Email"},"description":"Narrow to one rep. Omit for the whole team."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/sdr-activity/team-comparison":{"get":{"tags":["Analytics"],"summary":"Get Team Comparison","description":"Team averages - the baseline an individual rep is read against.","operationId":"get_team_comparison_analytics_outbound_sdr_activity_team_comparison_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/sdr-activity/{sdr_email}":{"get":{"tags":["Analytics"],"summary":"Get Sdr Activity By Email","description":"One rep's daily activity.\n\nA PLAIN path segment, where the app declares `{sdr_email:path}`. The\ngreedy converter would match across `/` and swallow every future route\nunder `/sdr-activity/`; an email address has no slash in it, and the\nalready-published `GET /analytics/sdr/{sdr_email}` sets the precedent one\nnamespace over.","operationId":"get_sdr_activity_by_email_analytics_outbound_sdr_activity__sdr_email__get","parameters":[{"name":"sdr_email","in":"path","required":true,"schema":{"type":"string","description":"The rep's email address.","title":"Sdr Email"},"description":"The rep's email address."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/audience/seniority":{"get":{"tags":["Analytics"],"summary":"Get Audience By Seniority","description":"Performance grouped by the CONTACT's seniority - C-level down to IC.\n\nAnswers who replies, not who was mailed. The three audience reports are\nthe ones that change targeting rather than copy.","operationId":"get_audience_by_seniority_analytics_outbound_audience_seniority_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/audience/industry":{"get":{"tags":["Analytics"],"summary":"Get Audience By Industry","description":"Performance grouped by the COMPANY's specific industry.","operationId":"get_audience_by_industry_analytics_outbound_audience_industry_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/audience/industry-group":{"get":{"tags":["Analytics"],"summary":"Get Audience By Industry Group","description":"The same, grouped into broad categories rather than exact industries.\n\nUse this one when the specific-industry split is too sparse to read -\n\"Technology\" has volume where \"Prepackaged Software\" does not.","operationId":"get_audience_by_industry_group_analytics_outbound_audience_industry_group_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/dashboards/manager":{"get":{"tags":["Analytics"],"summary":"Get Manager Dashboard","description":"Team overview, as an SDR manager reads it.","operationId":"get_manager_dashboard_analytics_outbound_dashboards_manager_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/dashboards/campaign":{"get":{"tags":["Analytics"],"summary":"Get Campaign Dashboard","description":"Sequence and campaign performance, as a campaign manager reads it.","operationId":"get_campaign_dashboard_analytics_outbound_dashboards_campaign_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/dashboards/executive":{"get":{"tags":["Analytics"],"summary":"Get Executive Dashboard","description":"The leadership roll-up. Cached for an hour - it is not a live view.","operationId":"get_executive_dashboard_analytics_outbound_dashboards_executive_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/dashboards/sdr/{sdr_email}":{"get":{"tags":["Analytics"],"summary":"Get Sdr Dashboard By Email","description":"One rep's dashboard, named explicitly.\n\n`GET /analytics/outbound/dashboards/sdr` is the key-holder's OWN\ndashboard; this one names the rep, so any key may read any rep's numbers.","operationId":"get_sdr_dashboard_by_email_analytics_outbound_dashboards_sdr__sdr_email__get","parameters":[{"name":"sdr_email","in":"path","required":true,"schema":{"type":"string","description":"The rep's email address.","title":"Sdr Email"},"description":"The rep's email address."},{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/outbound/dashboards/sdr":{"get":{"tags":["Analytics"],"summary":"Get My Sdr Dashboard","description":"The dashboard of the person who minted this key.\n\nThe rep is read from the key-holder's identity, so an organisation-scoped\nkey - which has no person behind it and would resolve to a synthetic\nsentinel address, answering empty - is refused with a 403 rather than\nhanded a dashboard that looks like a rep with no activity.","operationId":"get_my_sdr_dashboard_analytics_outbound_dashboards_sdr_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/product-usage/active-users":{"get":{"tags":["Analytics"],"summary":"Get Active Users","description":"Daily, weekly and monthly actives, plus stickiness (DAU/MAU).\n\nStickiness is the one to watch: DAU can climb on a hiring spree while the\nratio falls, which says the new people are not coming back.","operationId":"get_active_users_analytics_product_usage_active_users_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/product-usage/feature-adoption":{"get":{"tags":["Analytics"],"summary":"Get Feature Adoption","description":"Share of distinct actors who hit each lifecycle event in the window.","operationId":"get_feature_adoption_analytics_product_usage_feature_adoption_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/product-usage/top-pages":{"get":{"tags":["Analytics"],"summary":"Get Top Pages","description":"Busiest in-app pages and event names by volume.","operationId":"get_top_pages_analytics_product_usage_top_pages_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"description":"Rows per list.","default":20,"title":"Limit"},"description":"Rows per list."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/product-usage/activation-funnel":{"get":{"tags":["Analytics"],"summary":"Get Activation Funnel","description":"Sign-in to first list to first campaign launched.\n\nThe onboarding funnel: where a new seat stops before it becomes a user.","operationId":"get_activation_funnel_analytics_product_usage_activation_funnel_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/subscriptions/mrr":{"get":{"tags":["Analytics"],"summary":"Get Mrr","description":"MRR and ARR headline, plus the trailing trend.\n\nThe window sizes the TREND only - the headline is the current snapshot\neither way, so a shorter window makes the chart shorter, not the number\nsmaller.","operationId":"get_mrr_analytics_subscriptions_mrr_get","parameters":[{"name":"trailing_days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":7,"description":"Length of the trend series, in days.","default":90,"title":"Trailing Days"},"description":"Length of the trend series, in days."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/subscriptions/movement":{"get":{"tags":["Analytics"],"summary":"Get Movement","description":"The MRR waterfall: new, expansion, contraction, churned, reactivated.\n\nWhere `/mrr` says what the number is, this says what MOVED it.","operationId":"get_movement_analytics_subscriptions_movement_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/subscriptions/retention":{"get":{"tags":["Analytics"],"summary":"Get Retention","description":"Gross revenue churn, net revenue retention, and logo churn.","operationId":"get_retention_analytics_subscriptions_retention_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":7,"description":"Trailing window, in days.","default":90,"title":"Days"},"description":"Trailing window, in days."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/subscriptions/trial-conversion":{"get":{"tags":["Analytics"],"summary":"Get Trial Conversion","description":"Trial-to-paid rate and the median time it takes.","operationId":"get_trial_conversion_analytics_subscriptions_trial_conversion_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":7,"description":"Trailing window, in days.","default":60,"title":"Days"},"description":"Trailing window, in days."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/subscriptions/dunning":{"get":{"tags":["Analytics"],"summary":"Get Dunning","description":"Failed payments: still open, recovered, or written off.\n\nRevenue already earned and not yet collected - usually the cheapest money\non this router to go and get.","operationId":"get_dunning_analytics_subscriptions_dunning_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Size of the trailing window, in days, ending today (UTC).","default":30,"title":"Days"},"description":"Size of the trailing window, in days, ending today (UTC)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/subscriptions/plan-distribution":{"get":{"tags":["Analytics"],"summary":"Get Plan Distribution","description":"Active subscriptions and MRR per plan, as of now.\n\nA snapshot, so it takes no window - the only report here that does not.","operationId":"get_plan_distribution_analytics_subscriptions_plan_distribution_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/launchpad/activity-profile":{"get":{"tags":["Analytics"],"summary":"Get Launchpad Activity Profile","description":"The key-holder's detected persona and the activity types they actually do.","operationId":"get_launchpad_activity_profile_analytics_launchpad_activity_profile_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/launchpad/briefing":{"get":{"tags":["Analytics"],"summary":"Get Launchpad Briefing","description":"Today's briefing for the key-holder: what changed, and what needs them.","operationId":"get_launchpad_briefing_analytics_launchpad_briefing_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/launchpad/home-feed":{"get":{"tags":["Analytics"],"summary":"Get Launchpad Home Feed","description":"The key-holder's home feed: replies, meetings and recent activity.","operationId":"get_launchpad_home_feed_analytics_launchpad_home_feed_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/launchpad/smart-cards":{"get":{"tags":["Analytics"],"summary":"Get Launchpad Smart Cards","description":"Persona-ranked cards with live counts, as the copilot home screen shows them.","operationId":"get_launchpad_smart_cards_analytics_launchpad_smart_cards_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/launchpad/calendar/today":{"get":{"tags":["Analytics"],"summary":"Get Launchpad Calendar Today","description":"The key-holder's meetings for one day.","operationId":"get_launchpad_calendar_today_analytics_launchpad_calendar_today_get","parameters":[{"name":"date","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO date to read instead of today.","title":"Date"},"description":"ISO date to read instead of today."},{"name":"timezone","in":"query","required":false,"schema":{"type":"string","description":"IANA timezone the day boundaries are computed in.","default":"UTC","title":"Timezone"},"description":"IANA timezone the day boundaries are computed in."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/data-sources":{"get":{"tags":["Analytics"],"summary":"Get Analytics Data Sources","description":"Whether the org has the two sources the revenue and product reports read.\n\nThe payments-integration flag gates `/analytics/subscriptions/*` and the\nproduct-event flag gates `/analytics/product-usage/*`. Check it first: a\nreport over a source the org has not connected answers empty, not 404.","operationId":"get_analytics_data_sources_analytics_data_sources_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/revenue/lifecycle":{"put":{"tags":["Revenue"],"summary":"Update Lifecycles","description":"REPLACE the whole set of Revenue lifecycle stages.\n\nNot a merge. The posted `entries` array becomes the config, so a stage left\nout of it is DELETED along with the document defaults attached to it. Read\n`GET /lifecycle-stages` first and send the full list back with your change\napplied.\n\nAn entry with an empty `id` is treated as NEW and gets a fresh UUID. An\nentry that keeps its id keeps its stage document defaults - those are\nmerged forward by id, not rebuilt.","operationId":"update_lifecycles_revenue_lifecycle_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateLifecyclesRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/revenue/lifecycle/seed-defaults":{"post":{"tags":["Revenue"],"summary":"Seed Lifecycle Defaults","description":"Force-replace the stage config with the four seeded defaults.\n\nDESTRUCTIVE, and the app's own word for it is \"force-replace\": every\ncustom stage and every document default attached to it is gone. Recoverable\nonly by PUTting the old config back, so read it first if you might want it.","operationId":"seed_lifecycle_defaults_revenue_lifecycle_seed_defaults_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"deals:delete","x-graph8-lifecycle":"active"}},"/revenue/lifecycle/sync-lists":{"post":{"tags":["Revenue"],"summary":"Sync Lifecycle Lists","description":"Rebuild the saved list behind each lifecycle stage.\n\n202 and returns immediately - the rebuild runs in the background and there\nis no job id to poll, by the app's design. Call it after changing what a\nstage matches; membership is recomputed from the new rules.","operationId":"sync_lifecycle_lists_revenue_lifecycle_sync_lists_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/revenue/lifecycle/event-catalog":{"get":{"tags":["Revenue"],"summary":"Get Event Catalog","description":"Product events seen for this org in the last 30 days, busiest first.\n\nThe source of the `event_name` values a stage's `event_tracking` config\naccepts - configure one that has never fired and the stage tracks nothing.\n\nA brand-new org has no events table yet; that is an empty list, not an\nerror.","operationId":"get_event_catalog_revenue_lifecycle_event_catalog_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/revenue/stage-docs/defaults":{"get":{"tags":["Revenue"],"summary":"Get Stage Doc Defaults","description":"The whole document-defaults matrix - every stage, both entities.","operationId":"get_stage_doc_defaults_revenue_stage_docs_defaults_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/revenue/stage-docs/catalog":{"get":{"tags":["Revenue"],"summary":"Get Stage Doc Catalog","description":"Every document type a stage can generate, with its tier and grounding.\n\nThe source of the `type` values `PATCH /revenue/stage-docs/{id}/{entity}`\naccepts, and of the `tier` that decides what each one costs. Read it before\nconfiguring a slot: a type is only offerable for certain stages and\nentities, and both are listed here.","operationId":"get_stage_doc_catalog_revenue_stage_docs_catalog_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/revenue/stage-docs/{lifecycle_entry_id}/{entity}":{"get":{"tags":["Revenue"],"summary":"Get Stage Doc Slot","description":"One stage's document configuration for one entity kind.","operationId":"get_stage_doc_slot_revenue_stage_docs__lifecycle_entry_id___entity__get","parameters":[{"name":"lifecycle_entry_id","in":"path","required":true,"schema":{"type":"string","description":"Lifecycle stage id (UUID).","title":"Lifecycle Entry Id"},"description":"Lifecycle stage id (UUID)."},{"name":"entity","in":"path","required":true,"schema":{"enum":["company","contact"],"type":"string","description":"Which record kind the stage's documents are for. `company` and `contact` are configured independently - the same stage can generate documents for one and not the other.","title":"Entity"},"description":"Which record kind the stage's documents are for. `company` and `contact` are configured independently - the same stage can generate documents for one and not the other."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Revenue"],"summary":"Patch Stage Doc Slot","description":"Change one stage's document configuration for one entity kind.\n\nA MERGE: only the fields you send are applied. A field cannot be CLEARED\nby sending null - the app drops nulls from the patch rather than writing\nthem - so send the value you want instead.\n\n`auto_generate` is the switch that costs money: with it on, every record\nthat ARRIVES in this stage generates its `docs` immediately. `credit_cap`\nbounds that ongoing spend; the types come from\n`GET /revenue/stage-docs/catalog`.","operationId":"patch_stage_doc_slot_revenue_stage_docs__lifecycle_entry_id___entity__patch","parameters":[{"name":"lifecycle_entry_id","in":"path","required":true,"schema":{"type":"string","description":"Lifecycle stage id (UUID).","title":"Lifecycle Entry Id"},"description":"Lifecycle stage id (UUID)."},{"name":"entity","in":"path","required":true,"schema":{"enum":["company","contact"],"type":"string","description":"Which record kind the stage's documents are for. `company` and `contact` are configured independently - the same stage can generate documents for one and not the other.","title":"Entity"},"description":"Which record kind the stage's documents are for. `company` and `contact` are configured independently - the same stage can generate documents for one and not the other."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StageDocSlotPatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/revenue/stage-docs/{lifecycle_entry_id}/{entity}/reset":{"post":{"tags":["Revenue"],"summary":"Reset Stage Doc Slot","description":"Put one slot back to its seeded default. Discards the configuration.","operationId":"reset_stage_doc_slot_revenue_stage_docs__lifecycle_entry_id___entity__reset_post","parameters":[{"name":"lifecycle_entry_id","in":"path","required":true,"schema":{"type":"string","description":"Lifecycle stage id (UUID).","title":"Lifecycle Entry Id"},"description":"Lifecycle stage id (UUID)."},{"name":"entity","in":"path","required":true,"schema":{"enum":["company","contact"],"type":"string","description":"Which record kind the stage's documents are for. `company` and `contact` are configured independently - the same stage can generate documents for one and not the other.","title":"Entity"},"description":"Which record kind the stage's documents are for. `company` and `contact` are configured independently - the same stage can generate documents for one and not the other."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"deals:delete","x-graph8-lifecycle":"active"}},"/revenue/stage-docs/{lifecycle_entry_id}/{entity}/backfill/estimate":{"post":{"tags":["Revenue"],"summary":"Estimate Stage Doc Backfill","description":"What a backfill of this stage WOULD cost. Spends nothing.\n\nRecords affected, documents to generate, and credits. It counts and\nreturns; it queues no job and writes nothing. Call it first and use\n`estimated_credits` as the `max_credits` you send to the backfill below.","operationId":"estimate_stage_doc_backfill_revenue_stage_docs__lifecycle_entry_id___entity__backfill_estimate_post","parameters":[{"name":"lifecycle_entry_id","in":"path","required":true,"schema":{"type":"string","description":"Lifecycle stage id (UUID).","title":"Lifecycle Entry Id"},"description":"Lifecycle stage id (UUID)."},{"name":"entity","in":"path","required":true,"schema":{"enum":["company","contact"],"type":"string","description":"Which record kind the stage's documents are for. `company` and `contact` are configured independently - the same stage can generate documents for one and not the other.","title":"Entity"},"description":"Which record kind the stage's documents are for. `company` and `contact` are configured independently - the same stage can generate documents for one and not the other."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/revenue/stage-docs/{lifecycle_entry_id}/{entity}/backfill":{"post":{"tags":["Revenue"],"summary":"Start Stage Doc Backfill","description":"Generate this stage's documents for records already in it. SPENDS CREDITS.\n\nQueues a job and returns its id - poll `GET /revenue/backfills/{job_id}`.\nThe work is asynchronous, so a 202 here is not a completed backfill and not\na completed CHARGE either; the spend accrues as documents are produced.\n\n`max_credits` is a hard ceiling the worker enforces, not advice: the job\nstops the moment spend reaches it. `confirm` must be true - the app refuses\nthe call otherwise, deliberately, because this is the one route here that\ncosts money.","operationId":"start_stage_doc_backfill_revenue_stage_docs__lifecycle_entry_id___entity__backfill_post","parameters":[{"name":"lifecycle_entry_id","in":"path","required":true,"schema":{"type":"string","description":"Lifecycle stage id (UUID).","title":"Lifecycle Entry Id"},"description":"Lifecycle stage id (UUID)."},{"name":"entity","in":"path","required":true,"schema":{"enum":["company","contact"],"type":"string","description":"Which record kind the stage's documents are for. `company` and `contact` are configured independently - the same stage can generate documents for one and not the other.","title":"Entity"},"description":"Which record kind the stage's documents are for. `company` and `contact` are configured independently - the same stage can generate documents for one and not the other."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StageBackfillRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"knowledge:run","x-graph8-lifecycle":"active"}},"/revenue/backfills/estimate":{"post":{"tags":["Revenue"],"summary":"Estimate All Stage Doc Backfills","description":"What backfilling EVERY stage and both entities would cost. Spends nothing.\n\nThe totals plus a per-stage, per-entity breakdown. Published although the\nmatching \"start them all\" route is NOT (see the module docstring): seeing\nthe whole bill in one call is exactly what a caller needs before deciding\nwhich stages to backfill, and this one cannot spend anything.\n\nDeclared BEFORE `/backfills/{job_id}` so the literal wins. The two do not\nactually collide - one is a POST and the other a GET - but the ordering is\nthe habit, and the test checks the job route still resolves.","operationId":"estimate_all_stage_doc_backfills_revenue_backfills_estimate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/revenue/backfills/{job_id}":{"get":{"tags":["Revenue"],"summary":"Get Stage Doc Backfill Job","description":"How a backfill is going: status, progress, credits USED so far, errors.\n\n`credits_used` is the number that matters while a job runs - it is the\nspend that has actually happened, against the `max_credits` ceiling the\njob was started with.","operationId":"get_stage_doc_backfill_job_revenue_backfills__job_id__get","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","description":"Backfill job id (UUID).","title":"Job Id"},"description":"Backfill job id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/revenue/backfills/{job_id}/cancel":{"post":{"tags":["Revenue"],"summary":"Cancel Stage Doc Backfill Job","description":"Stop a running backfill, and stop it spending.\n\nIDEMPOTENT: a job that already finished or failed comes back with the\nstatus it has, not an error. Credits already spent are not refunded -\ncancelling stops the next document, it does not undo the last one.","operationId":"cancel_stage_doc_backfill_job_revenue_backfills__job_id__cancel_post","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","description":"Backfill job id (UUID).","title":"Job Id"},"description":"Backfill job id (UUID)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"deals:delete","x-graph8-lifecycle":"active"}},"/analytics/sales-report/cohort":{"post":{"tags":["Analytics"],"summary":"Compute Cohort","description":"The whole Sales Report for one filter, in one round trip.\n\nCohort plus funnel, pipeline, revenue and drill-down - thirteen sections\nresolved from a single deal cohort, which is the reason this is one call\nand not thirteen: the sections agree because they are computed over the\nsame resolved set, not re-derived.\n\nReads; writes nothing. It is a POST because the filter is a tree, not\nbecause it mutates - and it is tiered `read` for that reason.\n\nThe filter is `extra=\"forbid\"`: a misspelled key is a 422 naming it,\nrather than a silently wider result with a 200 on it.","operationId":"compute_cohort_analytics_sales_report_cohort_post","parameters":[{"name":"tz","in":"query","required":false,"schema":{"type":"string","description":"IANA timezone the local-day window bounds are computed in, e.g. `Asia/Tokyo`. Changes which deals fall inside the date range.","default":"UTC","title":"Tz"},"description":"IANA timezone the local-day window bounds are computed in, e.g. `Asia/Tokyo`. Changes which deals fall inside the date range."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FilterQueryDto"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/sales-report/cohort/explain":{"post":{"tags":["Analytics"],"summary":"Explain Cohort","description":"Which clause emptied the view.\n\nTakes the SAME body as `/cohort` and answers one\n`{label, lead_count, deal_count, measured}` row per progressively-built\nprefix of the filter - baseline, then +rep, then +lifecycle, and so on.\nRead the drop (`290 -> 57 -> 11 -> 0`) and the last step that moved is the\nclause that did it.\n\nCOUNTS ONLY, never rows - which is both what makes it affordable (about 26\ncount queries against `/cohort`'s full section fan-out) and why it is safe\nto call when `/cohort` itself would withhold person rows.","operationId":"explain_cohort_analytics_sales_report_cohort_explain_post","parameters":[{"name":"tz","in":"query","required":false,"schema":{"type":"string","description":"IANA timezone the local-day window bounds are computed in, e.g. `Asia/Tokyo`. Changes which deals fall inside the date range.","default":"UTC","title":"Tz"},"description":"IANA timezone the local-day window bounds are computed in, e.g. `Asia/Tokyo`. Changes which deals fall inside the date range."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FilterQueryDto"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/sales-report/filter-options":{"get":{"tags":["Analytics"],"summary":"Get Filter Options","description":"Every value the filter above will accept - reps, pipelines, stages,\nlifecycles, audiences, CRM sources.\n\nCall this before `/cohort` rather than guessing ids. Send `from` and `to`\ntogether to also get a `granularity` block saying which time buckets that\nwindow supports and why each refused one cannot.","operationId":"get_filter_options_analytics_sales_report_filter_options_get","parameters":[{"name":"from","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"description":"Start of the window to grade time-bucket granularities against. Must be sent WITH `to`. Omit both and the response is unchanged and carries no `granularity` block.","title":"From"},"description":"Start of the window to grade time-bucket granularities against. Must be sent WITH `to`. Omit both and the response is unchanged and carries no `granularity` block."},{"name":"to","in":"query","required":false,"schema":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"description":"End of that window. Must be sent WITH `from`.","title":"To"},"description":"End of that window. Must be sent WITH `from`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/sales-report/data-quality":{"get":{"tags":["Analytics"],"summary":"Get Data Quality","description":"Why a Sales Report section might be empty.\n\nUpstream linkage counts plus pre-rendered warnings. ALWAYS 200 - a failing\nsub-query degrades to zero rather than raising, so an empty `warnings` list\nmeans \"nothing breached a threshold\", not \"the check did not run\".\n\nRead this first when a number looks wrong. It is the difference between a\nfilter that matched nothing and a pipeline that is not wired up.","operationId":"get_data_quality_analytics_sales_report_data_quality_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"},"post":{"tags":["Analytics"],"summary":"Post Data Quality","description":"The same diagnostic, narrowed to the deals one filter resolves.\n\nA SECOND VERB rather than a changed one: the GET above is unchanged, so\n\"omit the filter and get today's answer\" stays a structural fact rather\nthan a claim about a defaulted parameter.\n\nOnly the DEAL-anchored figures move. The transcript counters, the 90-day\nevent total and the tier-rules flag come back org-wide on this path too,\nbecause no filter on this report can reach them.","operationId":"post_data_quality_analytics_sales_report_data_quality_post","parameters":[{"name":"tz","in":"query","required":false,"schema":{"type":"string","description":"IANA timezone the local-day window bounds are computed in, e.g. `Asia/Tokyo`. Changes which deals fall inside the date range.","default":"UTC","title":"Tz"},"description":"IANA timezone the local-day window bounds are computed in, e.g. `Asia/Tokyo`. Changes which deals fall inside the date range."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FilterQueryDto"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/sales-report/export":{"post":{"tags":["Analytics"],"summary":"Export Cohort Csv","description":"Download one section of the report - or the cohort drill-down - as CSV.\n\nTakes the `/cohort` filter plus `section`; an absent or unknown section is\nthe persons drill-down. The export is the SAME cohort the report shows,\nnarrowed by the same deal and lead scopes, so it can never be a wider\ndownload than the screen. Person rows are withheld exactly where `/cohort`\nwithholds them.\n\nReads; writes nothing. A POST only because the filter is a tree - tiered\n`read`.","operationId":"export_cohort_csv_analytics_sales_report_export_post","parameters":[{"name":"tz","in":"query","required":false,"schema":{"type":"string","description":"IANA timezone the local-day window bounds are computed in, e.g. `Asia/Tokyo`. Changes which deals fall inside the date range.","default":"UTC","title":"Tz"},"description":"IANA timezone the local-day window bounds are computed in, e.g. `Asia/Tokyo`. Changes which deals fall inside the date range."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ExportRequestDto"}}}},"responses":{"200":{"description":"One report section as CSV.","content":{"text/csv":{}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/ops":{"get":{"tags":["Ops (internal, cross-tenant, read-only)"],"summary":"Ops Index","description":"Self-describing index of the ops surface — start here.\n\nEvery list endpoint also accepts `?format=csv` for a spreadsheet-ready\ndownload. All endpoints are read-only.","operationId":"ops_index_ops_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/OpsIndex"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"ops:read","x-graph8-lifecycle":"active"}},"/ops/orgs/{org_id}/linkedin/actions":{"get":{"tags":["Ops (internal, cross-tenant, read-only)"],"summary":"List Linkedin Actions","description":"Per-contact LinkedIn action drill-down for one org, newest first.\n\nInterpretation guide (so counts are reported truthfully):\n- `failure_reason='skipped_too_distant'` (~90% of failures) = the target is\n  not 1st/2nd-degree reachable. An ELIGIBILITY skip — NOT a provider error,\n  rate limit, or account-health problem.\n- `note` null is the NORM (bare-invite strategy), not missing data.\n- A contact's `waiting_netrion` state = parked with this queue row in flight.","operationId":"list_linkedin_actions_ops_orgs__org_id__linkedin_actions_get","parameters":[{"name":"org_id","in":"path","required":true,"schema":{"type":"string","title":"Org Id"}},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"QUEUED | SENDING | SENT | ACCEPTED | FAILED","title":"Status"},"description":"QUEUED | SENDING | SENT | ACCEPTED | FAILED"},{"name":"kind","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"INVITE | MESSAGE","title":"Kind"},"description":"INVITE | MESSAGE"},{"name":"account_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Sender arlink account id (lia_...)","title":"Account Id"},"description":"Sender arlink account id (lia_...)"},{"name":"sequence_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Id"}},{"name":"since","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO timestamp; requested_at >= since","title":"Since"},"description":"ISO timestamp; requested_at >= since"},{"name":"until","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO timestamp; requested_at < until","title":"Until"},"description":"ISO timestamp; requested_at < until"},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":100,"title":"Limit"}},{"name":"format","in":"query","required":false,"schema":{"enum":["json","csv"],"type":"string","default":"json","title":"Format"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_OpsActionRow__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"ops:read","x-graph8-lifecycle":"active"}},"/ops/orgs/{org_id}/linkedin/actions/summary":{"get":{"tags":["Ops (internal, cross-tenant, read-only)"],"summary":"Summarize Linkedin Actions","description":"Sequence × sender × kind × status matrix — the at-a-glance volume view.","operationId":"summarize_linkedin_actions_ops_orgs__org_id__linkedin_actions_summary_get","parameters":[{"name":"org_id","in":"path","required":true,"schema":{"type":"string","title":"Org Id"}},{"name":"format","in":"query","required":false,"schema":{"enum":["json","csv"],"type":"string","default":"json","title":"Format"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_OpsActionSummaryRow__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"ops:read","x-graph8-lifecycle":"active"}},"/ops/orgs/{org_id}/linkedin/webhook-events":{"get":{"tags":["Ops (internal, cross-tenant, read-only)"],"summary":"Summarize Webhook Events","description":"Inbound webhook event-type counts + first/last seen for one org.\n\nThe underlying table is a dedupe ledger — NO payload is stored, so this\nendpoint cannot say *what* happened per event; read the effects instead\n(action status via /actions, contact state via /sequence-bindings).\n`inbox.message_received` explicitly EXCLUDES sequence-reply semantics; only\n`lead.message_received` means a tracked lead replied.","operationId":"summarize_webhook_events_ops_orgs__org_id__linkedin_webhook_events_get","parameters":[{"name":"org_id","in":"path","required":true,"schema":{"type":"string","title":"Org Id"}},{"name":"format","in":"query","required":false,"schema":{"enum":["json","csv"],"type":"string","default":"json","title":"Format"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_list_OpsWebhookEventSummary__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"ops:read","x-graph8-lifecycle":"active"}},"/ops/orgs/{org_id}/linkedin/sequence-bindings":{"get":{"tags":["Ops (internal, cross-tenant, read-only)"],"summary":"Get Sequence Bindings","description":"Sequence↔LinkedIn-sender bindings for one org, plus the unbound list.\n\n`unbound_live_sequences` is the high-signal field: a live sequence with a\nLinkedIn step but no active binding is configured but can NEVER send —\nthe measured platform-wide root cause of 'connected but not sending'.","operationId":"get_sequence_bindings_ops_orgs__org_id__linkedin_sequence_bindings_get","parameters":[{"name":"org_id","in":"path","required":true,"schema":{"type":"string","title":"Org Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OpsSequenceBindingsReport_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"ops:read","x-graph8-lifecycle":"active"}},"/landing-pages/agent-sessions/{session_id}":{"get":{"tags":["Landing Pages"],"summary":"Get Landing Page Source","description":"Return exact source for the draft bound to an edit session.","operationId":"get_landing_page_source_landing_pages_agent_sessions__session_id__get","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","title":"Session Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"landing-pages:read","x-graph8-lifecycle":"active"}},"/landing-pages/agent-sessions/{session_id}/patch":{"post":{"tags":["Landing Pages"],"summary":"Patch Landing Page","description":"Submit an exact patch using the handoff's selected approval mode.","operationId":"patch_landing_page_landing_pages_agent_sessions__session_id__patch_post","parameters":[{"name":"session_id","in":"path","required":true,"schema":{"type":"string","title":"Session Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LandingPagePatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"landing-pages:write","x-graph8-lifecycle":"active"}},"/landing-pages/{page_id}/agent-sessions":{"post":{"tags":["Landing Pages"],"summary":"Create Landing Page Agent Session","description":"Open a short-lived edit session against one landing page.\n\nReturns an `edit_session` id to pass to the two routes above. The session is\na LOCATOR, not a credential: it selects which draft the following calls act\non, and `get_api_user` still authenticates every one of them. It carries a\nTTL and is bound at creation to this org and this actor.\n\n`actor_email` is `str(user.id)`, byte-identical to what the read and patch\nroutes pass to `require_edit_session`. That is what closes the loop: a\nsession minted here resolves for the same key that minted it, and a mismatch\nwould make every subsequent call 404 against a session that plainly exists.\n\nNO OWNABILITY GUARD, unlike the agent routes. `agent_router` refuses a write\nfrom a key whose `actor_identities()` is empty, because an org key\nauthenticates as the shared constant `api-key@graph8.com`. The same constant\nlands in `actor_email` here, so two org keys in ONE org can read and patch\neach other's sessions. That is deliberate parity rather than an oversight:\nthe two sibling routes already bind on `str(user.id)` and already accept org\nkeys, so guarding only the create half would break the loop for exactly the\nkeys the other half still serves. The boundary that matters is unchanged --\n`require_edit_session` rejects a session from another ORG. Tightening all\nthree together belongs with the per-key identity work recorded in\n`.claude/agent-context/agent-runtime-api-key-door.md`.\n\nNOT SCOPE-GATED LOCALLY, unlike its two siblings, and that is deliberate\nrather than an oversight. They call `require_scope(\"landing-pages:...\")`,\nwhich makes `build_scope_policy` record them as `exempt`; an exempt route\npublishes no `x-graph8-scope`, so their requirement is real but invisible in\nthe contract -- and `landing-pages` is not a resource in\n`scope_vocabulary.json` at all, so the scope they name cannot be granted to\na key. It is inert today only because `require_scope` runs in soak mode by\ndefault. Leaving this route ungated puts it in the GOVERNED set, where\n`apply_scope_policy` attaches the gate and the bundle publishes\n`integrations:write` -- the resource this file is actually mapped to. The\nsiblings are left alone here: correcting them moves two published operations\nand belongs in its own change.","operationId":"create_landing_page_agent_session_landing_pages__page_id__agent_sessions_post","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","title":"Page Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/CreateAgentSessionRequest"},{"type":"null"}],"title":"Body"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_dict_str__Any__"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"integrations:write","x-graph8-lifecycle":"active"}},"/mcp/connection":{"get":{"tags":["MCP"],"summary":"Get Mcp Connection","description":"MCP connection facts for the authenticated org.\n\nTotal by construction: any tenant-schema trouble (table not yet created for\na brand-new org, transient DB error) answers the zero shape with\n``determined=False`` instead of 500 — the caller's collectors treat this\nroute as best-effort, and the flag keeps a DB blip from reading as positive\nnever-connected evidence.","operationId":"get_mcp_connection_mcp_connection_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_McpConnectionStatus_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/sandbox/status":{"get":{"tags":["sandbox"],"summary":"Sandbox status","description":"Report whether this is the developer sandbox and which org the key acts as.\n\nAnswers on every deployment. In the developer sandbox: ``sandbox: true``,\n``environment: \"sandbox\"``. Anywhere else: ``sandbox: false`` and\n``environment`` is ``\"live\"`` (production) or ``\"qa\"``. The other\n``/sandbox/*`` routes exist only in the sandbox and return 404 elsewhere.","operationId":"sandbox_status_sandbox_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SandboxStatusResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sandbox:read","x-graph8-lifecycle":"active"}},"/sandbox/outbox":{"get":{"tags":["sandbox"],"summary":"List simulated outbox","description":"SANDBOX ONLY. This endpoint exists only in the graph8 developer sandbox and returns 404 on the live platform. Call GET /sandbox/status to see which environment your key reaches.\n\nEvery simulated outbound side effect for your org, newest first.","operationId":"sandbox_outbox_sandbox_outbox_get","parameters":[{"name":"channel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by channel","title":"Channel"},"description":"Filter by channel"},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/OutboxListResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sandbox:read","x-graph8-lifecycle":"active","x-graph8-sandbox-only":true}},"/sandbox/failure-injection":{"get":{"tags":["sandbox"],"summary":"List failure rules","operationId":"sandbox_list_failure_rules_sandbox_failure_injection_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/FailureRulesResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sandbox:read","x-graph8-lifecycle":"active","x-graph8-sandbox-only":true,"description":"SANDBOX ONLY. This endpoint exists only in the graph8 developer sandbox and returns 404 on the live platform. Call GET /sandbox/status to see which environment your key reaches."},"put":{"tags":["sandbox"],"summary":"Set a failure rule","description":"SANDBOX ONLY. This endpoint exists only in the graph8 developer sandbox and returns 404 on the live platform. Call GET /sandbox/status to see which environment your key reaches.\n\nMake the next simulated sends on a channel fail the way you choose (M3-5).","operationId":"sandbox_set_failure_rule_sandbox_failure_injection_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/FailureRuleRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/FailureRulesResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sandbox:write","x-graph8-lifecycle":"active","x-graph8-sandbox-only":true},"delete":{"tags":["sandbox"],"summary":"Clear failure rules","operationId":"sandbox_clear_failure_rules_sandbox_failure_injection_delete","parameters":[{"name":"channel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Clear one channel only; omit for all","title":"Channel"},"description":"Clear one channel only; omit for all"},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/FailureRulesResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"sandbox:delete","x-graph8-lifecycle":"active","x-graph8-sandbox-only":true,"description":"SANDBOX ONLY. This endpoint exists only in the graph8 developer sandbox and returns 404 on the live platform. Call GET /sandbox/status to see which environment your key reaches."}},"/sandbox/fixtures/seed":{"post":{"tags":["sandbox"],"summary":"Seed sample data","description":"SANDBOX ONLY. This endpoint exists only in the graph8 developer sandbox and returns 404 on the live platform. Call GET /sandbox/status to see which environment your key reaches.\n\nInsert the standard sandbox fixture set into your org. Idempotent.","operationId":"sandbox_seed_fixtures_sandbox_fixtures_seed_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/FixtureActionResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sandbox:write","x-graph8-lifecycle":"active","x-graph8-sandbox-only":true}},"/sandbox/fixtures/reset":{"post":{"tags":["sandbox"],"summary":"Reset fixture data","description":"SANDBOX ONLY. This endpoint exists only in the graph8 developer sandbox and returns 404 on the live platform. Call GET /sandbox/status to see which environment your key reaches.\n\nDelete all seeded fixture rows for your org and reseed a fresh set.","operationId":"sandbox_reset_fixtures_sandbox_fixtures_reset_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/FixtureActionResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"sandbox:delete","x-graph8-lifecycle":"active","x-graph8-sandbox-only":true}},"/sandbox/fixtures/snapshot":{"post":{"tags":["sandbox"],"summary":"Snapshot fixture tables","description":"SANDBOX ONLY. This endpoint exists only in the graph8 developer sandbox and returns 404 on the live platform. Call GET /sandbox/status to see which environment your key reaches.\n\nSave the current contents of the fixture tables under a named snapshot.","operationId":"sandbox_snapshot_sandbox_fixtures_snapshot_post","parameters":[{"name":"name","in":"query","required":false,"schema":{"type":"string","minLength":1,"maxLength":64,"pattern":"^[A-Za-z0-9_\\-]+$","default":"default","title":"Name"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SnapshotActionResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sandbox:write","x-graph8-lifecycle":"active","x-graph8-sandbox-only":true}},"/sandbox/fixtures/restore":{"post":{"tags":["sandbox"],"summary":"Restore a snapshot","description":"SANDBOX ONLY. This endpoint exists only in the graph8 developer sandbox and returns 404 on the live platform. Call GET /sandbox/status to see which environment your key reaches.\n\nRestore the fixture rows to a previously saved snapshot.\n\nOnly sandbox-fixture rows (``meta.sandbox_fixture = true``) are replaced —\nany records you created through normal API calls in this sandbox are left\nuntouched. Snapshots are taken over the same fixture-scoped set, so a\nrestore round-trips exactly what ``/fixtures/snapshot`` captured.","operationId":"sandbox_restore_sandbox_fixtures_restore_post","parameters":[{"name":"name","in":"query","required":false,"schema":{"type":"string","minLength":1,"maxLength":64,"pattern":"^[A-Za-z0-9_\\-]+$","default":"default","title":"Name"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SnapshotActionResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"sandbox:delete","x-graph8-lifecycle":"active","x-graph8-sandbox-only":true}},"/health":{"get":{"tags":["health"],"summary":"API health","description":"Check that the graph8 Developer API is up. No API key is required.\n\nReturns ``{\"status\": \"ok\", \"service\": \"developer-api\"}`` whenever the API is\nserving requests. It does not check databases or downstream providers.","operationId":"api_health_health_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiHealthResponse"}}}}},"security":[],"x-graph8-tier":"read","x-graph8-lifecycle":"active"}},"/personas/generate":{"post":{"tags":["GTM Library"],"summary":"Generate Personas","description":"Research buyer personas for a website with AI (runs a model; billable).\n\nPinned personas survive; unpinned ones are replaced when saved.","operationId":"generate_personas_personas_generate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PersonaGenerateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/personas/from-global-doc":{"post":{"tags":["GTM Library"],"summary":"Fill Personas From Global Doc","description":"Create or complete personas from the finished persona-research document.\n\nIdempotent. A persona with a committee role already set is left alone.","operationId":"fill_personas_from_global_doc_personas_from_global_doc_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/PersonaFillFromDocRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/personas/{persona_id}/pin":{"post":{"tags":["GTM Library"],"summary":"Pin Persona","description":"Pin a persona so `POST /personas/generate` keeps it.","operationId":"pin_persona_personas__persona_id__pin_post","parameters":[{"name":"persona_id","in":"path","required":true,"schema":{"type":"string","description":"Persona id.","title":"Persona Id"},"description":"Persona id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/personas/{persona_id}/unpin":{"post":{"tags":["GTM Library"],"summary":"Unpin Persona","description":"Unpin a persona; the next generation may replace it.","operationId":"unpin_persona_personas__persona_id__unpin_post","parameters":[{"name":"persona_id","in":"path","required":true,"schema":{"type":"string","description":"Persona id.","title":"Persona Id"},"description":"Persona id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/icps/generate":{"post":{"tags":["GTM Library"],"summary":"Generate Icps","description":"Research ideal customer profiles for a website with AI (runs a model; billable).","operationId":"generate_icps_icps_generate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/IcpGenerateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/icps/{icp_id}/pin":{"post":{"tags":["GTM Library"],"summary":"Pin Icp","description":"Pin an ICP so `POST /icps/generate` keeps it.","operationId":"pin_icp_icps__icp_id__pin_post","parameters":[{"name":"icp_id","in":"path","required":true,"schema":{"type":"string","description":"ICP id.","title":"Icp Id"},"description":"ICP id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/icps/{icp_id}/unpin":{"post":{"tags":["GTM Library"],"summary":"Unpin Icp","description":"Unpin an ICP; the next generation may replace it.","operationId":"unpin_icp_icps__icp_id__unpin_post","parameters":[{"name":"icp_id","in":"path","required":true,"schema":{"type":"string","description":"ICP id.","title":"Icp Id"},"description":"ICP id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/tam":{"get":{"tags":["GTM Library"],"summary":"Get Tam","description":"The org's total-addressable-market definition.","operationId":"get_tam_tam_get","parameters":[{"name":"website_url","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Which website's TAM. Omit for the org's latest.","title":"Website Url"},"description":"Which website's TAM. Omit for the org's latest."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["GTM Library"],"summary":"Update Tam","description":"Replace the TAM definition. Records a new version authored by the key.","operationId":"update_tam_tam_patch","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TamUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"delete":{"tags":["GTM Library"],"summary":"Delete Tam","description":"Delete a TAM definition.","operationId":"delete_tam_tam_delete","parameters":[{"name":"website_url","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Which website's TAM to delete.","title":"Website Url"},"description":"Which website's TAM to delete."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/tam/generate":{"post":{"tags":["GTM Library"],"summary":"Generate Tam","description":"Define the TAM for a website with AI (runs a model; billable).","operationId":"generate_tam_tam_generate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TamGenerateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/tam/regenerate":{"post":{"tags":["GTM Library"],"summary":"Regenerate Tam","description":"Re-run the TAM definition with AI (runs a model; billable).","operationId":"regenerate_tam_tam_regenerate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TamGenerateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/committees":{"get":{"tags":["GTM Library"],"summary":"List Committees","description":"Every buying committee in the org, with member counts.","operationId":"list_committees_committees_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"post":{"tags":["GTM Library"],"summary":"Create Committee","description":"Create a buying committee.","operationId":"create_committee_committees_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CommitteeCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/committees/{committee_id}":{"get":{"tags":["GTM Library"],"summary":"Get Committee","description":"A committee with its full member roster.","operationId":"get_committee_committees__committee_id__get","parameters":[{"name":"committee_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Committee id.","title":"Committee Id"},"description":"Committee id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["GTM Library"],"summary":"Update Committee","description":"Rename a committee, edit its description, or make it the default.","operationId":"update_committee_committees__committee_id__patch","parameters":[{"name":"committee_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Committee id.","title":"Committee Id"},"description":"Committee id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CommitteeUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"delete":{"tags":["GTM Library"],"summary":"Delete Committee","description":"Delete a committee. Its member rows go with it.","operationId":"delete_committee_committees__committee_id__delete","parameters":[{"name":"committee_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Committee id.","title":"Committee Id"},"description":"Committee id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/committees/{committee_id}/members":{"put":{"tags":["GTM Library"],"summary":"Replace Committee Members","description":"Replace the committee's whole roster in one write.","operationId":"replace_committee_members_committees__committee_id__members_put","parameters":[{"name":"committee_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Committee id.","title":"Committee Id"},"description":"Committee id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CommitteeMembersRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_GtmLibraryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/calendar-invites":{"post":{"tags":["Calendar Invites"],"summary":"Create Calendar Invite","description":"Create a calendar invite. Sends nothing; share the returned `ics_url`.","operationId":"create_calendar_invite_calendar_invites_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CalendarInviteCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CalendarInvitePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/calendar-invites/{invite_id}":{"get":{"tags":["Calendar Invites"],"summary":"Get Calendar Invite","description":"One calendar invite.","operationId":"get_calendar_invite_calendar_invites__invite_id__get","parameters":[{"name":"invite_id","in":"path","required":true,"schema":{"type":"string","description":"Invite id.","title":"Invite Id"},"description":"Invite id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CalendarInvitePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"meetings:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Calendar Invites"],"summary":"Update Calendar Invite","description":"Edit an invite. Calendars subscribed to its `.ics` pick up the change.","operationId":"update_calendar_invite_calendar_invites__invite_id__patch","parameters":[{"name":"invite_id","in":"path","required":true,"schema":{"type":"string","description":"Invite id.","title":"Invite Id"},"description":"Invite id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CalendarInviteUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CalendarInvitePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"meetings:write","x-graph8-lifecycle":"active"}},"/intelligence/analyze":{"post":{"tags":["Company Intelligence"],"summary":"Analyze Website","description":"Start researching a website (scrapes and runs models; billable). Poll the returned task.","operationId":"analyze_website_intelligence_analyze_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/IntelligenceAnalyzeRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntelligencePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"knowledge:run","x-graph8-lifecycle":"active"}},"/intelligence/status/{task_id}":{"get":{"tags":["Company Intelligence"],"summary":"Get Intelligence Status","description":"Progress of an intelligence run, step by step.","operationId":"get_intelligence_status_intelligence_status__task_id__get","parameters":[{"name":"task_id","in":"path","required":true,"schema":{"type":"string","description":"Task id returned by `POST /intelligence/analyze`.","title":"Task Id"},"description":"Task id returned by `POST /intelligence/analyze`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntelligencePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/intelligence/data/{data_type}":{"get":{"tags":["Company Intelligence"],"summary":"Get Intelligence Data","description":"What one data source collected.","operationId":"get_intelligence_data_intelligence_data__data_type__get","parameters":[{"name":"data_type","in":"path","required":true,"schema":{"type":"string","description":"Which data source, e.g. `company_info`.","title":"Data Type"},"description":"Which data source, e.g. `company_info`."},{"name":"website_url","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Website Url"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntelligencePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/intelligence/latest-task":{"get":{"tags":["Company Intelligence"],"summary":"Get Latest Intelligence Task","description":"The org's most recent intelligence run.","operationId":"get_latest_intelligence_task_intelligence_latest_task_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntelligencePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/intelligence/documents":{"get":{"tags":["Company Intelligence"],"summary":"List Intelligence Documents","description":"Every intelligence document for the org.","operationId":"list_intelligence_documents_intelligence_documents_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntelligenceListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/intelligence/all/{website_url}":{"get":{"tags":["Company Intelligence"],"summary":"Get All Intelligence Data","description":"Everything collected for one website.","operationId":"get_all_intelligence_data_intelligence_all__website_url__get","parameters":[{"name":"website_url","in":"path","required":true,"schema":{"type":"string","description":"The researched website (host, no scheme).","title":"Website Url"},"description":"The researched website (host, no scheme)."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntelligencePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/intelligence/org-domain":{"get":{"tags":["Company Intelligence"],"summary":"Get Intelligence Org Domain","description":"The company domain recorded on the organisation.","operationId":"get_intelligence_org_domain_intelligence_org_domain_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntelligencePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/intelligence/retry":{"post":{"tags":["Company Intelligence"],"summary":"Retry Intelligence Source","description":"Re-collect one data source (scrapes and runs models; billable).","operationId":"retry_intelligence_source_intelligence_retry_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/IntelligenceSourceRetryRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntelligencePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"knowledge:run","x-graph8-lifecycle":"active"}},"/intelligence/primary-website":{"get":{"tags":["Company Intelligence"],"summary":"Get Intelligence Primary Website","description":"The website the org's intelligence was built from.","operationId":"get_intelligence_primary_website_intelligence_primary_website_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntelligencePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/intelligence":{"delete":{"tags":["Company Intelligence"],"summary":"Reset Intelligence","description":"Delete every intelligence record and run for the org and clear its primary website.\n\nGlobal-context documents are NOT touched.","operationId":"reset_intelligence_intelligence_delete","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntelligencePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"knowledge:delete","x-graph8-lifecycle":"active"}},"/global-context/generate/{doc_type}":{"post":{"tags":["Company Intelligence"],"summary":"Generate Global Context Document","description":"Generate ONE global-context document from the intelligence data (runs a model; billable).\n\nThe document appears under `GET /global-context/documents` when done.","operationId":"generate_global_context_document_global_context_generate__doc_type__post","parameters":[{"name":"doc_type","in":"path","required":true,"schema":{"type":"string","description":"The document type to (re)generate.","title":"Doc Type"},"description":"The document type to (re)generate."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/GlobalContextGenerateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntelligencePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"knowledge:run","x-graph8-lifecycle":"active"}},"/global-context/tree":{"get":{"tags":["Company Intelligence"],"summary":"Get Global Context Tree","description":"The global-context documents as a folder tree, with completion counts.","operationId":"get_global_context_tree_global_context_tree_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntelligencePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/global-context/tree/flat":{"get":{"tags":["Company Intelligence"],"summary":"Get Global Context Tree Flat","description":"The global-context documents as a flat list.","operationId":"get_global_context_tree_flat_global_context_tree_flat_get","parameters":[{"name":"folder_path","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only documents under this folder.","title":"Folder Path"},"description":"Only documents under this folder."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntelligencePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/research-reports/{report_id}/thinking":{"get":{"tags":["Company Intelligence"],"summary":"Get Research Report Thinking","description":"The recorded reasoning events of a research report, in order.","operationId":"get_research_report_thinking_research_reports__report_id__thinking_get","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","description":"Research report id.","title":"Report Id"},"description":"Research report id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntelligencePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"knowledge:read","x-graph8-lifecycle":"active"}},"/intelligence/brand-suggestions":{"post":{"tags":["Company Intelligence"],"summary":"Get Brand Suggestions","description":"The other websites the company links to from its homepage nav, header or footer. No credits.\n\nOnly for the organisation's own website (or any website before one is set); 400 otherwise, 429 when asked too often.\nAn empty `candidates` list on any fetch failure, so it never blocks setup.","operationId":"get_brand_suggestions_intelligence_brand_suggestions_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/IntelligenceBrandSuggestionsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/intelligence/data/{data_type}/fields/{field}":{"put":{"tags":["Company Intelligence"],"summary":"Set Intelligence Field","description":"Store a user edit to one editable field. Send the FULL edited value.\n\ngraph8 diffs it against the collected value and keeps the minimal override. 400 when the field is not editable or\nthe value is not valid for it.","operationId":"set_intelligence_field_intelligence_data__data_type__fields__field__put","parameters":[{"name":"data_type","in":"path","required":true,"schema":{"type":"string","description":"The intelligence document, e.g. `product_inventory` or `company_keywords`.","title":"Data Type"},"description":"The intelligence document, e.g. `product_inventory` or `company_keywords`."},{"name":"field","in":"path","required":true,"schema":{"type":"string","description":"The editable field of that document.","title":"Field"},"description":"The editable field of that document."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/IntelligenceFieldRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Company Intelligence"],"summary":"Reset Intelligence Field","description":"Reset one field back to the collected (source) value. Your other edits stay.","operationId":"reset_intelligence_field_intelligence_data__data_type__fields__field__delete","parameters":[{"name":"data_type","in":"path","required":true,"schema":{"type":"string","description":"The intelligence document, e.g. `product_inventory` or `company_keywords`.","title":"Data Type"},"description":"The intelligence document, e.g. `product_inventory` or `company_keywords`."},{"name":"field","in":"path","required":true,"schema":{"type":"string","description":"The field to reset.","title":"Field"},"description":"The field to reset."},{"name":"website_url","in":"query","required":true,"schema":{"type":"string","description":"The website the data was collected for.","title":"Website Url"},"description":"The website the data was collected for."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"knowledge:delete","x-graph8-lifecycle":"active"}},"/intelligence/data/{data_type}/overrides":{"delete":{"tags":["Company Intelligence"],"summary":"Reset All Intelligence Overrides","description":"Reset EVERY field of this document back to the collected value. All your edits to it are discarded.","operationId":"reset_all_intelligence_overrides_intelligence_data__data_type__overrides_delete","parameters":[{"name":"data_type","in":"path","required":true,"schema":{"type":"string","description":"The intelligence document, e.g. `product_inventory` or `company_keywords`.","title":"Data Type"},"description":"The intelligence document, e.g. `product_inventory` or `company_keywords`."},{"name":"website_url","in":"query","required":true,"schema":{"type":"string","description":"The website the data was collected for.","title":"Website Url"},"description":"The website the data was collected for."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"knowledge:delete","x-graph8-lifecycle":"active"}},"/intelligence/data/{data_type}/revise":{"post":{"tags":["Company Intelligence"],"summary":"Revise Intelligence","description":"Queue an AI rewrite of this document's editable fields. THIS SPENDS CREDITS (a model job).\n\nThe result lands as a DRAFT, not as an edit: read it, then `draft/accept` it (all or some fields) or `draft/discard`\nit. 402 when the organisation cannot pay, 400 when the document has no editable fields.","operationId":"revise_intelligence_intelligence_data__data_type__revise_post","parameters":[{"name":"data_type","in":"path","required":true,"schema":{"type":"string","description":"The intelligence document, e.g. `product_inventory` or `company_keywords`.","title":"Data Type"},"description":"The intelligence document, e.g. `product_inventory` or `company_keywords`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/IntelligenceReviseRequest"}}}},"responses":{"202":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"knowledge:run","x-graph8-lifecycle":"active"}},"/intelligence/data/{data_type}/draft/accept":{"post":{"tags":["Company Intelligence"],"summary":"Accept Intelligence Draft","description":"Apply the finished draft (all changed fields, or the `field_keys` you name) as overrides. 409 when there is none.","operationId":"accept_intelligence_draft_intelligence_data__data_type__draft_accept_post","parameters":[{"name":"data_type","in":"path","required":true,"schema":{"type":"string","description":"The intelligence document, e.g. `product_inventory` or `company_keywords`.","title":"Data Type"},"description":"The intelligence document, e.g. `product_inventory` or `company_keywords`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/IntelligenceDraftAcceptRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/intelligence/data/{data_type}/draft/discard":{"post":{"tags":["Company Intelligence"],"summary":"Discard Intelligence Draft","description":"Drop the draft. The live data and any edits you already accepted are untouched.","operationId":"discard_intelligence_draft_intelligence_data__data_type__draft_discard_post","parameters":[{"name":"data_type","in":"path","required":true,"schema":{"type":"string","description":"The intelligence document, e.g. `product_inventory` or `company_keywords`.","title":"Data Type"},"description":"The intelligence document, e.g. `product_inventory` or `company_keywords`."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/IntelligenceWebsiteRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_StudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"knowledge:write","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/workflows":{"get":{"tags":["Campaign Workflows"],"summary":"List Campaign Workflows","description":"Workflows linked to a campaign.","operationId":"list_campaign_workflows_campaigns__campaign_id__workflows_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id.","title":"Campaign Id"},"description":"Campaign id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CampaignWorkflowListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/workflows/{link_id}":{"put":{"tags":["Campaign Workflows"],"summary":"Update Campaign Workflow Link","description":"Change a link's role, display order or status.","operationId":"update_campaign_workflow_link_campaigns__campaign_id__workflows__link_id__put","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id.","title":"Campaign Id"},"description":"Campaign id."},{"name":"link_id","in":"path","required":true,"schema":{"type":"string","description":"Link id.","title":"Link Id"},"description":"Link id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CampaignWorkflowLinkUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CampaignWorkflowPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Campaign Workflows"],"summary":"Unlink Campaign Workflow","description":"Unlink a workflow from a campaign. The workflow itself is untouched.","operationId":"unlink_campaign_workflow_campaigns__campaign_id__workflows__link_id__delete","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id.","title":"Campaign Id"},"description":"Campaign id."},{"name":"link_id","in":"path","required":true,"schema":{"type":"string","description":"Link id.","title":"Link Id"},"description":"Link id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/campaigns/{campaign_id}/generation-progress":{"get":{"tags":["Campaign Workflows"],"summary":"Get Campaign Generation Progress","description":"How far a campaign's content generation has got: documents done, total, current.","operationId":"get_campaign_generation_progress_campaigns__campaign_id__generation_progress_get","parameters":[{"name":"campaign_id","in":"path","required":true,"schema":{"type":"string","description":"Campaign id.","title":"Campaign Id"},"description":"Campaign id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CampaignWorkflowPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/campaigns/ideas/save":{"post":{"tags":["Campaign Workflows"],"summary":"Save Campaign Ideas","description":"Store generated campaign ideas for the org.","operationId":"save_campaign_ideas_campaigns_ideas_save_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"array","items":{"type":"object","additionalProperties":true},"description":"Campaign ideas to store, as generated.","title":"Ideas"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_CampaignWorkflowPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/content/grids/{grid_id}/columns":{"post":{"tags":["Content Grid Skills"],"summary":"Add Content Grid Column","description":"Add a skill column to a grid. Nothing runs until you run it.","operationId":"add_content_grid_column_content_grids__grid_id__columns_post","parameters":[{"name":"grid_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Grid id.","title":"Grid Id"},"description":"Grid id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContentGridColumnRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContentGridSkillPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/content/grids/{grid_id}/columns/{column_id}":{"put":{"tags":["Content Grid Skills"],"summary":"Update Content Grid Column","description":"Rename a column or change its input mapping.","operationId":"update_content_grid_column_content_grids__grid_id__columns__column_id__put","parameters":[{"name":"grid_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Grid id.","title":"Grid Id"},"description":"Grid id."},{"name":"column_id","in":"path","required":true,"schema":{"type":"string","description":"Column id.","title":"Column Id"},"description":"Column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ContentGridColumnRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContentGridSkillPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Content Grid Skills"],"summary":"Remove Content Grid Column","description":"Remove a column from a grid.","operationId":"remove_content_grid_column_content_grids__grid_id__columns__column_id__delete","parameters":[{"name":"grid_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Grid id.","title":"Grid Id"},"description":"Grid id."},{"name":"column_id","in":"path","required":true,"schema":{"type":"string","description":"Column id.","title":"Column Id"},"description":"Column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContentGridSkillPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/content/grids/{grid_id}/rows/{row_id}/run/{column_id}":{"post":{"tags":["Content Grid Skills"],"summary":"Run Content Grid Cell","description":"Run one skill column on one row (runs a model; billable).","operationId":"run_content_grid_cell_content_grids__grid_id__rows__row_id__run__column_id__post","parameters":[{"name":"grid_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Grid id.","title":"Grid Id"},"description":"Grid id."},{"name":"row_id","in":"path","required":true,"schema":{"type":"string","description":"Row (content job) id.","title":"Row Id"},"description":"Row (content job) id."},{"name":"column_id","in":"path","required":true,"schema":{"type":"string","description":"Skill column id.","title":"Column Id"},"description":"Skill column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContentGridSkillPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/content/grids/{grid_id}/columns/{column_id}/run":{"post":{"tags":["Content Grid Skills"],"summary":"Run Content Grid Column","description":"Run one skill column on every row, or on `row_ids` (one model call per row; billable).","operationId":"run_content_grid_column_content_grids__grid_id__columns__column_id__run_post","parameters":[{"name":"grid_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Grid id.","title":"Grid Id"},"description":"Grid id."},{"name":"column_id","in":"path","required":true,"schema":{"type":"string","description":"Skill column id.","title":"Column Id"},"description":"Skill column id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"content":{"application/json":{"schema":{"anyOf":[{"$ref":"#/components/schemas/ContentGridRunRequest"},{"type":"null"}],"title":"Payload"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContentGridSkillPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/content/skill-runs/{execution_id}":{"get":{"tags":["Content Grid Skills"],"summary":"Get Content Skill Run","description":"One skill run: its status, inputs and output.","operationId":"get_content_skill_run_content_skill_runs__execution_id__get","parameters":[{"name":"execution_id","in":"path","required":true,"schema":{"type":"string","description":"Run id returned when the run was queued.","title":"Execution Id"},"description":"Run id returned when the run was queued."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ContentGridSkillPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/org-videos":{"get":{"tags":["Org Videos"],"summary":"List Org Videos","description":"The org's library videos, newest first.","operationId":"list_org_videos_org_videos_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgVideoListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/org-videos/{video_id}":{"get":{"tags":["Org Videos"],"summary":"Get Org Video","description":"One video. Poll this for a generated video's render progress.","operationId":"get_org_video_org_videos__video_id__get","parameters":[{"name":"video_id","in":"path","required":true,"schema":{"type":"string","description":"Video id.","title":"Video Id"},"description":"Video id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgVideoPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"},"patch":{"tags":["Org Videos"],"summary":"Update Org Video","description":"Edit a video's title, alt text, poster or tags. The file itself is immutable.","operationId":"update_org_video_org_videos__video_id__patch","parameters":[{"name":"video_id","in":"path","required":true,"schema":{"type":"string","description":"Video id.","title":"Video Id"},"description":"Video id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OrgVideoUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgVideoPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Org Videos"],"summary":"Delete Org Video","description":"Delete a video - soft by default, so it can be recovered; `hard=true` removes the file.","operationId":"delete_org_video_org_videos__video_id__delete","parameters":[{"name":"video_id","in":"path","required":true,"schema":{"type":"string","description":"Video id.","title":"Video Id"},"description":"Video id."},{"name":"hard","in":"query","required":false,"schema":{"type":"boolean","description":"Also remove the stored file. Irreversible.","default":false,"title":"Hard"},"description":"Also remove the stored file. Irreversible."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgVideoPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/org-videos/generate":{"post":{"tags":["Org Videos"],"summary":"Generate Org Video","description":"Render a storyboard of ready clips into a library video (charges the render fee).\n\nReturns at once with the video queued; poll `GET /org-videos/{video_id}`.","operationId":"generate_org_video_org_videos_generate_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OrgVideoGenerateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgVideoPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"campaigns:run","x-graph8-lifecycle":"active"}},"/org-videos/upload":{"post":{"tags":["Org Videos"],"summary":"Upload Org Video","description":"Upload a video to the library. An identical file already there is returned instead.","operationId":"upload_org_video_org_videos_upload_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_upload_org_video_org_videos_upload_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgVideoPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/radar/aeo/dossier/{probe_id}":{"get":{"tags":["Radar Reports"],"summary":"Get Radar Aeo Dossier","description":"One probe's answer dossier: its recent runs, oldest first, with citations.","operationId":"get_radar_aeo_dossier_radar_aeo_dossier__probe_id__get","parameters":[{"name":"probe_id","in":"path","required":true,"schema":{"type":"string","description":"AEO probe id.","title":"Probe Id"},"description":"AEO probe id."},{"name":"engine","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only this answer engine.","title":"Engine"},"description":"Only this answer engine."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RadarReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/radar/aeo/sources":{"get":{"tags":["Radar Reports"],"summary":"Get Radar Aeo Sources","description":"The domains answer engines cite, classified as yours, a rival's or neutral.","operationId":"get_radar_aeo_sources_radar_aeo_sources_get","parameters":[{"name":"days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"default":30,"title":"Days"}},{"name":"engine","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only this answer engine.","title":"Engine"},"description":"Only this answer engine."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RadarReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/radar/reports":{"post":{"tags":["Radar Reports"],"summary":"Create Radar Report","description":"Start a deep-dive report on one capability for one audience (runs a model; billable).","operationId":"create_radar_report_radar_reports_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RadarReportCreateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RadarReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"intent:run","x-graph8-lifecycle":"active"},"get":{"tags":["Radar Reports"],"summary":"List Radar Reports","description":"Deep-dive reports and their status (no content).","operationId":"list_radar_reports_radar_reports_get","parameters":[{"name":"capability_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Capability Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RadarReportListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/radar/reports/{report_id}/html":{"get":{"tags":["Radar Reports"],"summary":"Get Radar Report Html","description":"A completed report as a self-contained HTML document.","operationId":"get_radar_report_html_radar_reports__report_id__html_get","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","maxLength":64,"title":"Report Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"The report as one HTML document.","content":{"text/html":{}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/radar/reports/{report_id}/pdf":{"get":{"tags":["Radar Reports"],"summary":"Get Radar Report Pdf","description":"A completed report as a PDF. 409 while it is still generating.","operationId":"get_radar_report_pdf_radar_reports__report_id__pdf_get","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","maxLength":64,"title":"Report Id"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"The report as a PDF.","content":{"application/pdf":{}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/radar/case-files":{"get":{"tags":["Radar Reports"],"summary":"List Radar Case Files","description":"The org's case files, newest first (at most 100).","operationId":"list_radar_case_files_radar_case_files_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only case files in this status.","title":"Status"},"description":"Only case files in this status."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RadarReportListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"intent:read","x-graph8-lifecycle":"active"}},"/radar/case-files/{case_id}/action":{"post":{"tags":["Radar Reports"],"summary":"Act On Radar Case File","description":"Record the decision on a case file. `mark_played` also opens a CRM task for it.","operationId":"act_on_radar_case_file_radar_case_files__case_id__action_post","parameters":[{"name":"case_id","in":"path","required":true,"schema":{"type":"string","description":"Case file id.","title":"Case Id"},"description":"Case file id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RadarCaseFileActionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RadarReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"intent:write","x-graph8-lifecycle":"active"}},"/activities/metrics/summary":{"get":{"tags":["Revenue Records"],"summary":"Get Activity Metrics","description":"Activity counts and trends over a window.","operationId":"get_activity_metrics_activities_metrics_summary_get","parameters":[{"name":"period_days","in":"query","required":false,"schema":{"type":"integer","description":"Days to analyse.","default":30,"title":"Period Days"},"description":"Days to analyse."},{"name":"owner_id","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only this owner's activities.","title":"Owner Id"},"description":"Only this owner's activities."},{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only activities from this source.","title":"Source"},"description":"Only activities from this source."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/activities/{activity_id}":{"get":{"tags":["Revenue Records"],"summary":"Get Activity","description":"One activity.","operationId":"get_activity_activities__activity_id__get","parameters":[{"name":"activity_id","in":"path","required":true,"schema":{"type":"string","description":"Activity id.","title":"Activity Id"},"description":"Activity id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/activities":{"get":{"tags":["Revenue Records"],"summary":"List Company Activities","description":"A company's activity timeline, newest first.","operationId":"list_company_activities_companies__company_id__activities_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Company id.","title":"Company Id"},"description":"Company id."},{"name":"activity_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Activity Type"}},{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only activities from this source.","title":"Source"},"description":"Only activities from this source."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueRecordListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/deals/{deal_id}/activities":{"get":{"tags":["Revenue Records"],"summary":"List Deal Activities","description":"A deal's activity timeline, newest first.","operationId":"list_deal_activities_deals__deal_id__activities_get","parameters":[{"name":"deal_id","in":"path","required":true,"schema":{"type":"string","description":"Deal id.","title":"Deal Id"},"description":"Deal id."},{"name":"activity_type","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Activity Type"}},{"name":"source","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only activities from this source.","title":"Source"},"description":"Only activities from this source."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueRecordListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/lifecycle-snapshot":{"get":{"tags":["Revenue Records"],"summary":"Get Company Lifecycle Snapshot","description":"The lifecycle-aware snapshot of one company: stage, and the event counts that matter for it.","operationId":"get_company_lifecycle_snapshot_companies__company_id__lifecycle_snapshot_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Account, company-extension or company id.","title":"Company Id"},"description":"Account, company-extension or company id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/contacts/{contact_id}/lifecycle-snapshot":{"get":{"tags":["Revenue Records"],"summary":"Get Contact Lifecycle Snapshot","description":"The lifecycle-aware snapshot of one contact.","operationId":"get_contact_lifecycle_snapshot_contacts__contact_id__lifecycle_snapshot_get","parameters":[{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/companies/{company_id}/events":{"get":{"tags":["Revenue Records"],"summary":"Get Company Events","description":"Counts of named product events for a company over a window.","operationId":"get_company_events_companies__company_id__events_get","parameters":[{"name":"company_id","in":"path","required":true,"schema":{"type":"string","description":"Account or company id.","title":"Company Id"},"description":"Account or company id."},{"name":"names","in":"query","required":true,"schema":{"type":"string","description":"Comma-separated event names.","title":"Names"},"description":"Comma-separated event names."},{"name":"window_days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"default":30,"title":"Window Days"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/lifecycle-contacts":{"get":{"tags":["Revenue Records"],"summary":"List Lifecycle Contacts","description":"The contacts in one lifecycle stage.","operationId":"list_lifecycle_contacts_lifecycle_contacts_get","parameters":[{"name":"lifecycle_id","in":"query","required":true,"schema":{"type":"string","description":"The lifecycle stage.","title":"Lifecycle Id"},"description":"The lifecycle stage."},{"name":"skip","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Skip"}},{"name":"limit","in":"query","required":false,"schema":{"anyOf":[{"type":"integer","minimum":1},{"type":"null"}],"title":"Limit"}},{"name":"company_status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Status"}},{"name":"search","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Search"}},{"name":"agFilterModel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"JSON grid filter model.","title":"Agfiltermodel"},"description":"JSON grid filter model."},{"name":"agSortModel","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"JSON grid sort model.","title":"Agsortmodel"},"description":"JSON grid sort model."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"}},"/lifecycle-contacts/unlock":{"post":{"tags":["Revenue Records"],"summary":"Unlock Lifecycle Contacts","description":"Unlock contact details in a lifecycle stage (charges credits per newly unlocked contact).\n\nContacts already unlocked cost nothing.","operationId":"unlock_lifecycle_contacts_lifecycle_contacts_unlock_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LifecycleContactsUnlockRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"deals:run","x-graph8-lifecycle":"active"}},"/revenue/plans":{"get":{"tags":["Revenue Records"],"summary":"List Revenue Plans","description":"The org's plan catalog, active plans first.","operationId":"list_revenue_plans_revenue_plans_get","parameters":[{"name":"include_inactive","in":"query","required":false,"schema":{"type":"boolean","default":false,"title":"Include Inactive"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"deals:read","x-graph8-lifecycle":"active"},"post":{"tags":["Revenue Records"],"summary":"Create Revenue Plan","description":"Add a plan. The slug is unique per org.","operationId":"create_revenue_plan_revenue_plans_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RevenuePlanCreateRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/revenue/plans/normalize":{"post":{"tags":["Revenue Records"],"summary":"Normalize Revenue Plans","description":"Match every account's free-text plan to a catalog plan, and report what did not match.","operationId":"normalize_revenue_plans_revenue_plans_normalize_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/revenue/plans/{plan_id}":{"put":{"tags":["Revenue Records"],"summary":"Update Revenue Plan","description":"Edit any subset of a plan's fields.","operationId":"update_revenue_plan_revenue_plans__plan_id__put","parameters":[{"name":"plan_id","in":"path","required":true,"schema":{"type":"string","description":"Plan id.","title":"Plan Id"},"description":"Plan id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RevenuePlanUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Revenue Records"],"summary":"Deactivate Revenue Plan","description":"Deactivate a plan. Accounts already on it keep it; it just stops being offered.","operationId":"deactivate_revenue_plan_revenue_plans__plan_id__delete","parameters":[{"name":"plan_id","in":"path","required":true,"schema":{"type":"string","description":"Plan id.","title":"Plan Id"},"description":"Plan id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"deals:delete","x-graph8-lifecycle":"active"}},"/deals/pipelines/{pipeline_id}/default":{"put":{"tags":["Revenue Records"],"summary":"Set Default Pipeline","description":"Make a pipeline the org default. Every other pipeline stops being the default.","operationId":"set_default_pipeline_deals_pipelines__pipeline_id__default_put","parameters":[{"name":"pipeline_id","in":"path","required":true,"schema":{"type":"string","description":"Pipeline id.","title":"Pipeline Id"},"description":"Pipeline id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueRecordPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"deals:write","x-graph8-lifecycle":"active"}},"/lifecycle-contacts/lead-statuses":{"get":{"tags":["Revenue Records"],"summary":"List Lifecycle Lead Statuses","description":"The CRM lead statuses present on the organisation's contacts: the options of the grid's Lead Status filter.\n\nStatuses are a per-CRM picklist (Salesforce, HubSpot, ...), so the list comes from the data. Read-only.","operationId":"list_lifecycle_lead_statuses_lifecycle_contacts_lead_statuses_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LifecycleLeadStatusesPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/lifecycle-contacts/export":{"post":{"tags":["Revenue Records"],"summary":"Export Lifecycle Contacts","description":"Download the stage Contacts grid as CSV: the same rows, order and visible columns the grid shows.\n\nLocked contacts export masked, as on screen. Needs `data:export:bulk` (Owner and Admin have it) and an explicit\n`contacts:run` grant; a key with no contact access is refused. The export is audited and alerts the admins.","operationId":"export_lifecycle_contacts_lifecycle_contacts_export_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LifecycleContactsExportBody"}}}},"responses":{"200":{"description":"The stage Contacts grid as a CSV file","content":{"text/csv":{"schema":{"type":"string","format":"binary"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-response-format":"binary","x-graph8-tier":"external","x-graph8-scope":"contacts:run","x-graph8-lifecycle":"active"}},"/lifecycle-accounts/export":{"post":{"tags":["Revenue Records"],"summary":"Export Lifecycle Accounts","description":"Download the lifecycle Companies grid as CSV: the same rows, order and visible columns the grid shows.\n\nNeeds `data:export:bulk` (Owner and Admin have it) and an explicit `companies:run` grant. A key whose company\nscope is \"none\" is refused 403. The export is audited and alerts the admins.","operationId":"export_lifecycle_accounts_lifecycle_accounts_export_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LifecycleAccountsExportBody"}}}},"responses":{"200":{"description":"The lifecycle Companies grid as a CSV file","content":{"text/csv":{"schema":{"type":"string","format":"binary"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-response-format":"binary","x-graph8-tier":"external","x-graph8-scope":"companies:run","x-graph8-lifecycle":"active"}},"/analytics/team/dashboard":{"get":{"tags":["Revenue Analytics"],"summary":"Get Team Revenue Dashboard","description":"Team-wide pipeline, win and activity metrics over a window.","operationId":"get_team_revenue_dashboard_analytics_team_dashboard_get","parameters":[{"name":"period_days","in":"query","required":false,"schema":{"type":"integer","description":"Days to look back.","default":30,"title":"Period Days"},"description":"Days to look back."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueAnalyticsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/team/pipeline-velocity":{"get":{"tags":["Revenue Analytics"],"summary":"Get Team Pipeline Velocity","description":"How deals move through pipeline stages: time in stage and conversion.","operationId":"get_team_pipeline_velocity_analytics_team_pipeline_velocity_get","parameters":[{"name":"period_days","in":"query","required":false,"schema":{"type":"integer","description":"Days to analyse.","default":90,"title":"Period Days"},"description":"Days to analyse."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueAnalyticsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/team/conversion-funnel":{"get":{"tags":["Revenue Analytics"],"summary":"Get Team Conversion Funnel","description":"Account/lead to closed-deal conversion, stage by stage.","operationId":"get_team_conversion_funnel_analytics_team_conversion_funnel_get","parameters":[{"name":"period_days","in":"query","required":false,"schema":{"type":"integer","description":"Days to analyse.","default":90,"title":"Period Days"},"description":"Days to analyse."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueAnalyticsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/team/forecast":{"get":{"tags":["Revenue Analytics"],"summary":"Get Team Revenue Forecast","description":"Revenue forecast from the open pipeline and stage probabilities.","operationId":"get_team_revenue_forecast_analytics_team_forecast_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueAnalyticsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/attribution/sender-performance":{"get":{"tags":["Revenue Analytics"],"summary":"Get Sender Performance","description":"Sends, clicks and signups per mailbox, sending domain and channel.","operationId":"get_sender_performance_analytics_attribution_sender_performance_get","parameters":[{"name":"since_days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Lookback window.","default":30,"title":"Since Days"},"description":"Lookback window."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueAnalyticsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/analytics/attribution/acquisition-breakdown":{"get":{"tags":["Revenue Analytics"],"summary":"Get Acquisition Breakdown","description":"Signups by UTM source and campaign.","operationId":"get_acquisition_breakdown_analytics_attribution_acquisition_breakdown_get","parameters":[{"name":"since_days","in":"query","required":false,"schema":{"type":"integer","maximum":365,"minimum":1,"description":"Lookback window.","default":30,"title":"Since Days"},"description":"Lookback window."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RevenueAnalyticsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"analytics:read","x-graph8-lifecycle":"active"}},"/provider-usage":{"get":{"tags":["Provider Usage"],"summary":"Get Provider Usage","description":"Usage statistics for every configured provider.","operationId":"get_provider_usage_provider_usage_get","parameters":[{"name":"providers","in":"query","required":false,"schema":{"anyOf":[{"type":"array","items":{"type":"string"}},{"type":"null"}],"description":"Only these providers.","title":"Providers"},"description":"Only these providers."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ProviderUsagePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/provider-usage/{provider}":{"get":{"tags":["Provider Usage"],"summary":"Get Single Provider Usage","description":"Usage statistics for one provider.","operationId":"get_single_provider_usage_provider_usage__provider__get","parameters":[{"name":"provider","in":"path","required":true,"schema":{"type":"string","description":"Provider name.","title":"Provider"},"description":"Provider name."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ProviderUsagePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/provider-usage/refresh":{"post":{"tags":["Provider Usage"],"summary":"Refresh Provider Usage","description":"Re-read usage from the providers now (calls each provider's API with the org's key).","operationId":"refresh_provider_usage_provider_usage_refresh_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ProviderUsageRefreshRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ProviderUsagePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/provider-usage/sync":{"post":{"tags":["Provider Usage"],"summary":"Sync Provider Usage Now","description":"Sync this org's usage from every provider immediately.","operationId":"sync_provider_usage_now_provider_usage_sync_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ProviderUsagePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"integrations:run","x-graph8-lifecycle":"active"}},"/provider-usage/cache":{"delete":{"tags":["Provider Usage"],"summary":"Clear Provider Usage Cache","description":"Drop the cached figures so the next read goes to the providers.","operationId":"clear_provider_usage_cache_provider_usage_cache_delete","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_ProviderUsagePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"integrations:delete","x-graph8-lifecycle":"active"}},"/org/ai-connections":{"get":{"tags":["Org Governance"],"summary":"List Ai Connections","description":"Every org member's connected AI clients, with 30-day call counts.","operationId":"list_ai_connections_org_ai_connections_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgGovernancePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/org/ai-connections/config":{"get":{"tags":["Org Governance"],"summary":"Get Ai Connections Config","description":"What is recorded about AI-client calls, and for how long.","operationId":"get_ai_connections_config_org_ai_connections_config_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgGovernancePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Org Governance"],"summary":"Update Ai Connections Config","description":"Change what is recorded about AI-client calls and how long it is kept.","operationId":"update_ai_connections_config_org_ai_connections_config_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AiConnectionsConfigRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgGovernancePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/ai-connections/{user_id}/summary":{"get":{"tags":["Org Governance"],"summary":"Get Ai Connection Summary","description":"One member's AI-client usage over 30 days, by day and tool.","operationId":"get_ai_connection_summary_org_ai_connections__user_id__summary_get","parameters":[{"name":"user_id","in":"path","required":true,"schema":{"type":"string","description":"The org member's user id.","title":"User Id"},"description":"The org member's user id."},{"name":"client_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only this AI client.","title":"Client Key"},"description":"Only this AI client."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgGovernancePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/org/ai-connections/{user_id}/calls":{"get":{"tags":["Org Governance"],"summary":"List Ai Connection Calls","description":"One member's recorded AI-client calls, newest first, cursor-paged.","operationId":"list_ai_connection_calls_org_ai_connections__user_id__calls_get","parameters":[{"name":"user_id","in":"path","required":true,"schema":{"type":"string","description":"The org member's user id.","title":"User Id"},"description":"The org member's user id."},{"name":"client_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Client Key"}},{"name":"tool_name","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Tool Name"}},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"enum":["success","error"],"type":"string"},{"type":"null"}],"title":"Status"}},{"name":"from","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO timestamp, inclusive.","title":"From"},"description":"ISO timestamp, inclusive."},{"name":"to","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ISO timestamp, exclusive.","title":"To"},"description":"ISO timestamp, exclusive."},{"name":"cursor","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Cursor"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgGovernancePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/org/ai-connections/{user_id}/blocks":{"post":{"tags":["Org Governance"],"summary":"Block Ai Connection","description":"Block a member's AI client (or all of them) from calling graph8.","operationId":"block_ai_connection_org_ai_connections__user_id__blocks_post","parameters":[{"name":"user_id","in":"path","required":true,"schema":{"type":"string","description":"The org member's user id.","title":"User Id"},"description":"The org member's user id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AiConnectionBlockRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgGovernancePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Org Governance"],"summary":"Resume Ai Connection","description":"Lift a block.","operationId":"resume_ai_connection_org_ai_connections__user_id__blocks_delete","parameters":[{"name":"user_id","in":"path","required":true,"schema":{"type":"string","description":"The org member's user id.","title":"User Id"},"description":"The org member's user id."},{"name":"client_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only this client. Omit to lift every block.","title":"Client Key"},"description":"Only this client. Omit to lift every block."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgGovernancePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"account:delete","x-graph8-lifecycle":"active"}},"/org/ai-connections/{user_id}/activity":{"delete":{"tags":["Org Governance"],"summary":"Delete Ai Connection Activity","description":"Permanently delete a member's recorded AI-client activity.","operationId":"delete_ai_connection_activity_org_ai_connections__user_id__activity_delete","parameters":[{"name":"user_id","in":"path","required":true,"schema":{"type":"string","description":"The org member's user id.","title":"User Id"},"description":"The org member's user id."},{"name":"client_key","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only this client's records.","title":"Client Key"},"description":"Only this client's records."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgGovernancePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"account:delete","x-graph8-lifecycle":"active"}},"/org/infrastructure":{"get":{"tags":["Org Governance"],"summary":"Get Infrastructure Profile","description":"The provider catalogue per category and the org's current selections.","operationId":"get_infrastructure_profile_org_infrastructure_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgGovernancePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Org Governance"],"summary":"Update Infrastructure Profile","description":"Set the org's provider selections, category by category.","operationId":"update_infrastructure_profile_org_infrastructure_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/InfrastructureProfileUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgGovernancePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/infrastructure/security-roles":{"get":{"tags":["Org Governance"],"summary":"List Security Roles","description":"The security-responsibility roles and who holds each.","operationId":"list_security_roles_org_infrastructure_security_roles_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgGovernancePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/org/infrastructure/security-roles/{role_id}":{"put":{"tags":["Org Governance"],"summary":"Assign Security Role","description":"Make a team member responsible for a security role.","operationId":"assign_security_role_org_infrastructure_security_roles__role_id__put","parameters":[{"name":"role_id","in":"path","required":true,"schema":{"type":"string","description":"Security role id.","title":"Role Id"},"description":"Security role id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SecurityRoleAssignRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgGovernancePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Org Governance"],"summary":"Unassign Security Role","description":"Clear who holds a security role. The role itself stays.","operationId":"unassign_security_role_org_infrastructure_security_roles__role_id__delete","parameters":[{"name":"role_id","in":"path","required":true,"schema":{"type":"string","description":"Security role id.","title":"Role Id"},"description":"Security role id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgGovernancePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"account:delete","x-graph8-lifecycle":"active"}},"/org/rep-limits":{"get":{"tags":["Org Governance"],"summary":"List Rep Limits","description":"Every member's limits and current usage.","operationId":"list_rep_limits_org_rep_limits_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgGovernancePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/org/rep-limits/{user_id}":{"put":{"tags":["Org Governance"],"summary":"Set Rep Limits Override","description":"Override one member's limits, or `reset` them to the role default.","operationId":"set_rep_limits_override_org_rep_limits__user_id__put","parameters":[{"name":"user_id","in":"path","required":true,"schema":{"type":"string","description":"The member's user id.","title":"User Id"},"description":"The member's user id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RepLimitsOverrideRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgGovernancePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/org/suppression-settings":{"get":{"tags":["Org Governance"],"summary":"Get Suppression Settings","description":"Whether a contact's opt-out on one channel covers every channel.","operationId":"get_suppression_settings_org_suppression_settings_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgGovernancePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"},"put":{"tags":["Org Governance"],"summary":"Update Suppression Settings","description":"Set the opt-out scope. Applies to opt-outs from now on; existing ones keep their scope.","operationId":"update_suppression_settings_org_suppression_settings_put","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuppressionSettingsRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_OrgGovernancePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/bug-reports":{"post":{"tags":["Bug Reports"],"summary":"Create Bug Report","description":"File a bug with graph8. It is routed to the engineer who owns the product area.","operationId":"create_bug_report_bug_reports_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"$ref":"#/components/schemas/Body_create_bug_report_bug_reports_post"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BugReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"},"get":{"tags":["Bug Reports"],"summary":"List Bug Reports","description":"The bug reports this key filed, newest first.","operationId":"list_bug_reports_bug_reports_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"enum":["open","in_progress","resolved","closed"],"type":"string"},{"type":"null"}],"title":"Status"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":50,"title":"Limit"}},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"default":0,"title":"Offset"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BugReportListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/bug-reports/board":{"get":{"tags":["Bug Reports"],"summary":"Get Bug Board","description":"The reports this key filed, grouped by status with their live tracker state.","operationId":"get_bug_board_bug_reports_board_get","parameters":[{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"enum":["open","in_progress","resolved","closed"],"type":"string"},{"type":"null"}],"title":"Status"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BugReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/bug-reports/{report_id}":{"get":{"tags":["Bug Reports"],"summary":"Get Bug Report","description":"One bug report, with comments and screenshots.","operationId":"get_bug_report_bug_reports__report_id__get","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Bug report id.","title":"Report Id"},"description":"Bug report id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BugReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/bug-reports/{report_id}/screenshots":{"get":{"tags":["Bug Reports"],"summary":"Get Bug Report Screenshots","description":"Time-limited download links for a report's screenshots.","operationId":"get_bug_report_screenshots_bug_reports__report_id__screenshots_get","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Bug report id.","title":"Report Id"},"description":"Bug report id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BugReportListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"account:read","x-graph8-lifecycle":"active"}},"/bug-reports/{report_id}/comments":{"post":{"tags":["Bug Reports"],"summary":"Comment On Bug Report","description":"Add a comment. graph8's engineer sees it on the tracked issue.","operationId":"comment_on_bug_report_bug_reports__report_id__comments_post","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Bug report id.","title":"Report Id"},"description":"Bug report id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BugReportCommentRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BugReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/bug-reports/{report_id}/close":{"post":{"tags":["Bug Reports"],"summary":"Close Bug Report","description":"Close a report you filed. The tracked issue is closed too.","operationId":"close_bug_report_bug_reports__report_id__close_post","parameters":[{"name":"report_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Bug report id.","title":"Report Id"},"description":"Bug report id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_BugReportPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"account:write","x-graph8-lifecycle":"active"}},"/integrations/google-workspace":{"get":{"tags":["Integration Status"],"summary":"Get Google Workspace Status","description":"Whether Google Workspace is connected, and what it is configured to do.","operationId":"get_google_workspace_status_integrations_google_workspace_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntegrationStatusPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/google-workspace/test":{"post":{"tags":["Integration Status"],"summary":"Test Google Workspace Connection","description":"Check the stored Workspace connection still authenticates. Changes nothing.","operationId":"test_google_workspace_connection_integrations_google_workspace_test_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntegrationStatusPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/google-workspace/folders":{"get":{"tags":["Integration Status"],"summary":"List Google Drive Folders","description":"Drive folders the connected Workspace can see, one level at a time.","operationId":"list_google_drive_folders_integrations_google_workspace_folders_get","parameters":[{"name":"parent_id","in":"query","required":false,"schema":{"type":"string","description":"Parent folder id; `root` for the top level.","default":"root","title":"Parent Id"},"description":"Parent folder id; `root` for the top level."},{"name":"view","in":"query","required":false,"schema":{"enum":["my_drive","shared_drives","shared_with_me"],"type":"string","default":"my_drive","title":"View"}},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Page Size"}},{"name":"page_token","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Page Token"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntegrationStatusPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/google-workspace/folders/{folder_id}/files":{"get":{"tags":["Integration Status"],"summary":"List Google Drive Folder Files","description":"The files in one Drive folder.","operationId":"list_google_drive_folder_files_integrations_google_workspace_folders__folder_id__files_get","parameters":[{"name":"folder_id","in":"path","required":true,"schema":{"type":"string","description":"Drive folder id.","title":"Folder Id"},"description":"Drive folder id."},{"name":"page_size","in":"query","required":false,"schema":{"type":"integer","maximum":200,"minimum":1,"default":50,"title":"Page Size"}},{"name":"page_token","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Page Token"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntegrationStatusPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/roam/status":{"get":{"tags":["Integration Status"],"summary":"Get Roam Status","description":"Whether Roam is connected for notifications and the copilot bridge.","operationId":"get_roam_status_integrations_roam_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntegrationStatusPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/integrations/slack/status":{"get":{"tags":["Integration Status"],"summary":"Get Slack Status","description":"Whether Slack is connected, and to which workspace.","operationId":"get_slack_status_integrations_slack_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_IntegrationStatusPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"integrations:read","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/generate":{"post":{"tags":["Newsletter"],"summary":"Generate Newsletter Issue","description":"Generate the issue's content with AI (runs a model; billable). Poll `generation-status`.","operationId":"generate_newsletter_issue_newsletters__newsletter_id__issues__issue_id__generate_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id.","title":"Newsletter Id"},"description":"Newsletter id."},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id.","title":"Issue Id"},"description":"Issue id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NewsletterIssueGenerateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterStudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/conversation":{"get":{"tags":["Newsletter"],"summary":"Get Newsletter Issue Conversation","description":"The AI editing conversation recorded on an issue.","operationId":"get_newsletter_issue_conversation_newsletters__newsletter_id__issues__issue_id__conversation_get","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id.","title":"Newsletter Id"},"description":"Newsletter id."},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id.","title":"Issue Id"},"description":"Issue id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterStudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/versions":{"get":{"tags":["Newsletter"],"summary":"List Newsletter Issue Versions","description":"An issue's saved versions, newest first.","operationId":"list_newsletter_issue_versions_newsletters__newsletter_id__issues__issue_id__versions_get","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id.","title":"Newsletter Id"},"description":"Newsletter id."},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id.","title":"Issue Id"},"description":"Issue id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterStudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/issues/{issue_id}/versions/{version_num}/restore":{"post":{"tags":["Newsletter"],"summary":"Restore Newsletter Issue Version","description":"Restore an issue to one of its saved versions.","operationId":"restore_newsletter_issue_version_newsletters__newsletter_id__issues__issue_id__versions__version_num__restore_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id.","title":"Newsletter Id"},"description":"Newsletter id."},{"name":"issue_id","in":"path","required":true,"schema":{"type":"integer","description":"Issue id.","title":"Issue Id"},"description":"Issue id."},{"name":"version_num","in":"path","required":true,"schema":{"type":"integer","description":"The version to restore.","title":"Version Num"},"description":"The version to restore."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterStudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"}},"/newsletters/templates/{template_id}":{"patch":{"tags":["Newsletter"],"summary":"Update Newsletter Template","description":"Edit a template's name, subject, preview text or HTML.","operationId":"update_newsletter_template_newsletters_templates__template_id__patch","parameters":[{"name":"template_id","in":"path","required":true,"schema":{"type":"integer","description":"Template id.","title":"Template Id"},"description":"Template id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NewsletterTemplateUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterStudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Newsletter"],"summary":"Delete Newsletter Template","description":"Delete an org template.","operationId":"delete_newsletter_template_newsletters_templates__template_id__delete","parameters":[{"name":"template_id","in":"path","required":true,"schema":{"type":"integer","description":"Template id.","title":"Template Id"},"description":"Template id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterStudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"newsletter:delete","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/subscribers/verify/preview":{"post":{"tags":["Newsletter"],"summary":"Preview Newsletter Subscriber Verification","description":"How many addresses would be verified and what it would cost. Free; submits nothing.","operationId":"preview_newsletter_subscriber_verification_newsletters__newsletter_id__subscribers_verify_preview_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id.","title":"Newsletter Id"},"description":"Newsletter id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterStudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/subscribers/verify":{"post":{"tags":["Newsletter"],"summary":"Verify Newsletter Subscribers","description":"Verify every unverified subscriber address (charges credits per address).","operationId":"verify_newsletter_subscribers_newsletters__newsletter_id__subscribers_verify_post","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id.","title":"Newsletter Id"},"description":"Newsletter id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterStudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"newsletter:run","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/subscribers/verify/status":{"get":{"tags":["Newsletter"],"summary":"Get Newsletter Subscriber Verification","description":"The verification job in progress for this newsletter, if any.","operationId":"get_newsletter_subscriber_verification_newsletters__newsletter_id__subscribers_verify_status_get","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id.","title":"Newsletter Id"},"description":"Newsletter id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterStudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"newsletter:read","x-graph8-lifecycle":"active"}},"/newsletters/{newsletter_id}/campaign":{"put":{"tags":["Newsletter"],"summary":"Link Newsletter Campaign","description":"Link a Studio campaign to this newsletter (replaces any existing link).","operationId":"link_newsletter_campaign_newsletters__newsletter_id__campaign_put","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id.","title":"Newsletter Id"},"description":"Newsletter id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/NewsletterCampaignLinkRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterStudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"newsletter:write","x-graph8-lifecycle":"active"},"delete":{"tags":["Newsletter"],"summary":"Unlink Newsletter Campaign","description":"Unlink the Studio campaign. The campaign itself is untouched.","operationId":"unlink_newsletter_campaign_newsletters__newsletter_id__campaign_delete","parameters":[{"name":"newsletter_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Newsletter id.","title":"Newsletter Id"},"description":"Newsletter id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_NewsletterStudioPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"newsletter:delete","x-graph8-lifecycle":"active"}},"/search/global":{"get":{"tags":["Search"],"summary":"Search Workspace Global","description":"One query across companies, people, campaigns, deals and documents.","operationId":"search_workspace_global_search_global_get","parameters":[{"name":"q","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":100,"title":"Q"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":10,"minimum":1,"description":"Results per category.","default":5,"title":"Limit"},"description":"Results per category."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkspaceSearchPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"search:read","x-graph8-lifecycle":"active"}},"/search/entities":{"get":{"tags":["Search"],"summary":"Search Crm Entities","description":"Companies, contacts and deals by name, limited to what this key may see.","operationId":"search_crm_entities_search_entities_get","parameters":[{"name":"q","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":100,"title":"Q"}},{"name":"types","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Comma-separated: companies,contacts,deals.","title":"Types"},"description":"Comma-separated: companies,contacts,deals."},{"name":"lifecycle","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Only records in this lifecycle stage.","title":"Lifecycle"},"description":"Only records in this lifecycle stage."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":25,"minimum":1,"description":"Results per record type.","default":10,"title":"Limit"},"description":"Results per record type."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkspaceSearchPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"search:read","x-graph8-lifecycle":"active"}},"/search/workspace":{"post":{"tags":["Search"],"summary":"Search Workspace Documents","description":"Search Studio's documents, intelligence and research.","operationId":"search_workspace_documents_search_workspace_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/WorkspaceSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkspaceSearchPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"search:read","x-graph8-lifecycle":"active"}},"/search/workspace/sections":{"get":{"tags":["Search"],"summary":"List Workspace Search Sections","description":"The sections workspace search can be filtered to.","operationId":"list_workspace_search_sections_search_workspace_sections_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkspaceSearchListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"search:read","x-graph8-lifecycle":"active"}},"/search/workspace/suggest":{"post":{"tags":["Search"],"summary":"Suggest Workspace Search","description":"Completions for a partial workspace query.","operationId":"suggest_workspace_search_search_workspace_suggest_post","parameters":[{"name":"query","in":"query","required":true,"schema":{"type":"string","minLength":1,"description":"What has been typed so far.","title":"Query"},"description":"What has been typed so far."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkspaceSearchPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"search:read","x-graph8-lifecycle":"active"}},"/search/signals/options":{"get":{"tags":["Search"],"summary":"Get Search Signal Options","description":"Company categories, detected technologies and data horizons for signal filters.","operationId":"get_search_signal_options_search_signals_options_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkspaceSearchPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"search:read","x-graph8-lifecycle":"active"}},"/search/signals/tech":{"get":{"tags":["Search"],"summary":"Suggest Search Signal Tech","description":"Technologies matching a partial name, with how many companies use each.","operationId":"suggest_search_signal_tech_search_signals_tech_get","parameters":[{"name":"q","in":"query","required":true,"schema":{"type":"string","minLength":1,"maxLength":60,"title":"Q"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkspaceSearchListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"search:read","x-graph8-lifecycle":"active"}},"/search/signals/preview":{"post":{"tags":["Search"],"summary":"Preview Search Signal","description":"How many companies one signal matches on its own, before any other filter.","operationId":"preview_search_signal_search_signals_preview_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SearchSignalFilter"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_WorkspaceSearchPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"search:read","x-graph8-lifecycle":"active"}},"/records/{entity_type}/{entity_id}/role-slots":{"get":{"tags":["Record Roles"],"summary":"Get Record Role Slots","description":"Who currently holds each role slot on a record.","operationId":"get_record_role_slots_records__entity_type___entity_id__role_slots_get","parameters":[{"name":"entity_type","in":"path","required":true,"schema":{"enum":["contact","company","deal"],"type":"string","description":"`contact`, `company` or `deal`.","title":"Entity Type"},"description":"`contact`, `company` or `deal`."},{"name":"entity_id","in":"path","required":true,"schema":{"type":"string","description":"The record id.","title":"Entity Id"},"description":"The record id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RecordRolePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/records/{entity_type}/{entity_id}/role-history":{"get":{"tags":["Record Roles"],"summary":"Get Record Role History","description":"Every assignment and unassignment on a record, in order.","operationId":"get_record_role_history_records__entity_type___entity_id__role_history_get","parameters":[{"name":"entity_type","in":"path","required":true,"schema":{"enum":["contact","company","deal"],"type":"string","description":"`contact`, `company` or `deal`.","title":"Entity Type"},"description":"`contact`, `company` or `deal`."},{"name":"entity_id","in":"path","required":true,"schema":{"type":"string","description":"The record id.","title":"Entity Id"},"description":"The record id."},{"name":"slot","in":"query","required":false,"schema":{"anyOf":[{"enum":["sdr","ae","csm"],"type":"string"},{"type":"null"}],"description":"Only this slot.","title":"Slot"},"description":"Only this slot."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Limit"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RecordRolePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"contacts:read","x-graph8-lifecycle":"active"}},"/records/{entity_type}/{entity_id}/role-assignments":{"post":{"tags":["Record Roles"],"summary":"Assign Record Role","description":"Put a member in a role slot. Other slots are untouched; re-assigning the holder is a no-op.","operationId":"assign_record_role_records__entity_type___entity_id__role_assignments_post","parameters":[{"name":"entity_type","in":"path","required":true,"schema":{"enum":["contact","company","deal"],"type":"string","description":"`contact`, `company` or `deal`.","title":"Entity Type"},"description":"`contact`, `company` or `deal`."},{"name":"entity_id","in":"path","required":true,"schema":{"type":"string","description":"The record id.","title":"Entity Id"},"description":"The record id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RecordRoleAssignRequest"}}}},"responses":{"201":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RecordRolePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"contacts:write","x-graph8-lifecycle":"active"}},"/records/{entity_type}/{entity_id}/role-assignments/{role_slot}":{"delete":{"tags":["Record Roles"],"summary":"Clear Record Role","description":"Clear a role slot. Recorded as an unassignment in the history.","operationId":"clear_record_role_records__entity_type___entity_id__role_assignments__role_slot__delete","parameters":[{"name":"entity_type","in":"path","required":true,"schema":{"enum":["contact","company","deal"],"type":"string","description":"`contact`, `company` or `deal`.","title":"Entity Type"},"description":"`contact`, `company` or `deal`."},{"name":"entity_id","in":"path","required":true,"schema":{"type":"string","description":"The record id.","title":"Entity Id"},"description":"The record id."},{"name":"role_slot","in":"path","required":true,"schema":{"enum":["sdr","ae","csm"],"type":"string","description":"The slot to clear.","title":"Role Slot"},"description":"The slot to clear."},{"name":"reason","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Recorded on the history row.","default":"manual_reassign","title":"Reason"},"description":"Recorded on the history row."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_RecordRolePayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"contacts:delete","x-graph8-lifecycle":"active"}},"/leads/bulk-delete":{"post":{"tags":["Leads"],"summary":"Remove Leads","description":"Remove leads from their lists. Returns how many were removed.","operationId":"remove_leads_leads_bulk_delete_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LeadRemoveRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LeadContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"lists:delete","x-graph8-lifecycle":"active"}},"/leads/generate-content/batches":{"post":{"tags":["Leads"],"summary":"Start Lead Content Batch","description":"Write outreach for up to 100 leads in the background (one model call each; billable).","operationId":"start_lead_content_batch_leads_generate_content_batches_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LeadContentBatchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LeadContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/leads/generate-content/batches/{batch_id}":{"get":{"tags":["Leads"],"summary":"Get Lead Content Batch","description":"A batch's progress, with each finished lead's content.","operationId":"get_lead_content_batch_leads_generate_content_batches__batch_id__get","parameters":[{"name":"batch_id","in":"path","required":true,"schema":{"type":"string","description":"Batch id returned when the batch started.","title":"Batch Id"},"description":"Batch id returned when the batch started."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LeadContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"lists:read","x-graph8-lifecycle":"active"}},"/leads/{lead_id}/generate-content":{"post":{"tags":["Leads"],"summary":"Generate Lead Content","description":"Write a personalised outreach email for one lead (runs a model; billable). Sends nothing.","operationId":"generate_lead_content_leads__lead_id__generate_content_post","parameters":[{"name":"lead_id","in":"path","required":true,"schema":{"type":"integer","description":"Lead id.","title":"Lead Id"},"description":"Lead id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LeadContentRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_LeadContentPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"billable","x-graph8-scope":"lists:run","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/contacts/{contact_id}/pause":{"post":{"tags":["Sequences"],"summary":"Pause Sequence Contact","description":"Pause one contact in a sequence. Everyone else keeps going.","operationId":"pause_sequence_contact_sequences__sequence_id__contacts__contact_id__pause_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceOpsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"sequences:write","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/contacts/{contact_id}/resume":{"post":{"tags":["Sequences"],"summary":"Resume Sequence Contact","description":"Resume a paused contact. Its next step can send.","operationId":"resume_sequence_contact_sequences__sequence_id__contacts__contact_id__resume_post","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"contact_id","in":"path","required":true,"schema":{"type":"integer","description":"Contact id.","title":"Contact Id"},"description":"Contact id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceOpsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"external","x-graph8-scope":"sequences:run","x-graph8-lifecycle":"active"}},"/sequences/{sequence_id}/reports":{"get":{"tags":["Sequences"],"summary":"Get Sequence Reports","description":"A sequence's full report: overview, funnel, engagement, 30-day timeline, distribution.","operationId":"get_sequence_reports_sequences__sequence_id__reports_get","parameters":[{"name":"sequence_id","in":"path","required":true,"schema":{"type":"string","description":"Sequence id.","title":"Sequence Id"},"description":"Sequence id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceOpsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/sequence-jobs/{job_id}":{"get":{"tags":["Sequences"],"summary":"Get Sequence Job","description":"The status of a background sequence job the org started.","operationId":"get_sequence_job_sequence_jobs__job_id__get","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","description":"Background job id.","title":"Job Id"},"description":"Background job id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_SequenceOpsPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"sequences:read","x-graph8-lifecycle":"active"}},"/deliverability/recovery":{"get":{"tags":["Deliverability"],"summary":"Get Mailbox Recovery Overview","description":"Mailboxes by domain with their lifecycle, pending retirements, and the spare pool.","operationId":"get_mailbox_recovery_overview_deliverability_recovery_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxRecoveryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/deliverability/recovery/mailboxes/{mailbox_id}/history":{"get":{"tags":["Deliverability"],"summary":"Get Mailbox Recovery History","description":"A mailbox's daily health snapshots over the last `weeks` weeks.","operationId":"get_mailbox_recovery_history_deliverability_recovery_mailboxes__mailbox_id__history_get","parameters":[{"name":"mailbox_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Mailbox id.","title":"Mailbox Id"},"description":"Mailbox id."},{"name":"weeks","in":"query","required":false,"schema":{"type":"integer","maximum":52,"minimum":1,"default":10,"title":"Weeks"}},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxRecoveryListPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/deliverability/recovery/decide":{"post":{"tags":["Deliverability"],"summary":"Decide Mailbox Retirement","description":"Approve or reject a proposed retirement. Approving schedules the mailbox's cancellation.","operationId":"decide_mailbox_retirement_deliverability_recovery_decide_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RetirementDecisionRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxRecoveryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"destructive","x-graph8-scope":"campaigns:delete","x-graph8-lifecycle":"active"}},"/deliverability/recovery/undo":{"post":{"tags":["Deliverability"],"summary":"Undo Mailbox Retirement","description":"Reverse an approved retirement while its grace window is open.","operationId":"undo_mailbox_retirement_deliverability_recovery_undo_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/RetirementUndoRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxRecoveryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/deliverability/recovery/removal-requests":{"post":{"tags":["Deliverability"],"summary":"Create Blocklist Removal Request","description":"Track a removal request you filed for a blocklisted sending domain.","operationId":"create_blocklist_removal_request_deliverability_recovery_removal_requests_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BlocklistRemovalCreateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxRecoveryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/deliverability/recovery/removal-requests/{request_id}":{"patch":{"tags":["Deliverability"],"summary":"Update Blocklist Removal Request","description":"Attach or change the ticket reference on a removal request.","operationId":"update_blocklist_removal_request_deliverability_recovery_removal_requests__request_id__patch","parameters":[{"name":"request_id","in":"path","required":true,"schema":{"type":"integer","minimum":1,"description":"Removal request id.","title":"Request Id"},"description":"Removal request id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BlocklistRemovalUpdateRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxRecoveryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"campaigns:write","x-graph8-lifecycle":"active"}},"/deliverability/blocklist/check":{"post":{"tags":["Deliverability"],"summary":"Check Domain Blocklist","description":"Blocklist verdicts for up to 50 domains. `null` means unknown, never \"clean\".","operationId":"check_domain_blocklist_deliverability_blocklist_check_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BlocklistCheckRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_MailboxRecoveryPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"campaigns:read","x-graph8-lifecycle":"active"}},"/app-page-sources":{"get":{"tags":["App Pages"],"summary":"List App Page Source Kinds","description":"The source families an app page can be built over, and whether each is available.","operationId":"list_app_page_source_kinds_app_page_sources_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppPageSourceCatalogPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"active"}},"/app-page-sources/{source_kind}/instances":{"get":{"tags":["App Pages"],"summary":"List App Page Source Instances","description":"The sources of one family this org can build a page over.","operationId":"list_app_page_source_instances_app_page_sources__source_kind__instances_get","parameters":[{"name":"source_kind","in":"path","required":true,"schema":{"type":"string","description":"A family `kind` from `GET /app-page-sources`.","title":"Source Kind"},"description":"A family `kind` from `GET /app-page-sources`."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":100,"minimum":1,"default":100,"title":"Limit"}},{"name":"query","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Filter by name.","title":"Query"},"description":"Filter by name."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppPageSourceCatalogPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"apps:read","x-graph8-lifecycle":"active"}},"/app-pages/{page_id}/sources":{"put":{"tags":["App Pages"],"summary":"Replace App Page Sources","description":"Replace a page's sources. Each new source is validated before anything is written.","operationId":"replace_app_page_sources_app_pages__page_id__sources_put","parameters":[{"name":"page_id","in":"path","required":true,"schema":{"type":"string","description":"App page id.","title":"Page Id"},"description":"App page id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AppPageSourcesReplaceRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_AppPageSourcesPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"write","x-graph8-scope":"apps:write","x-graph8-lifecycle":"active"}},"/envelopes/{envelope_id}/pdf":{"get":{"tags":["E-Sign"],"summary":"Download Signed Envelope","description":"The signed PDF of a completed envelope.","operationId":"download_signed_envelope_envelopes__envelope_id__pdf_get","parameters":[{"name":"envelope_id","in":"path","required":true,"schema":{"type":"string","format":"uuid","description":"Envelope id.","title":"Envelope Id"},"description":"Envelope id."},{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"The signed document.","content":{"application/pdf":{}}},"404":{"description":"No such envelope in this org, or it is not signed yet."},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"quotes:read","x-graph8-lifecycle":"active"}},"/phone-numbers/search":{"post":{"tags":["Phone Numbers"],"summary":"Search Available Phone Numbers","description":"Numbers a carrier has available to buy. Buy one with `POST /phone-numbers/purchase`.","operationId":"search_available_phone_numbers_phone_numbers_search_post","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PhoneNumberSearchRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PhoneNumberSearchPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}},"/phone-numbers/a2p/status":{"get":{"tags":["Phone Numbers"],"summary":"Get Phone A2P Status","description":"Where the org's A2P 10DLC registration stands, and whether its inputs are complete.","operationId":"get_phone_a2p_status_phone_numbers_a2p_status_get","parameters":[{"name":"Authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}},{"name":"X-Target-Org-Id","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"X-Target-Org-Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ApiResponse_PhoneA2pStatusPayload_"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-graph8-tier":"read","x-graph8-scope":"voice:read","x-graph8-lifecycle":"active"}}},"components":{"schemas":{"A2pRegisterRequest":{"properties":{"brand_inputs":{"additionalProperties":true,"type":"object","title":"Brand Inputs","description":"The legal business behind the messages: `legal_business_name` (required before registration can start), plus `ein`, `address`, `website`, `business_type`, `vertical` and whatever else the carrier registry asks for."},"campaign_inputs":{"additionalProperties":true,"type":"object","title":"Campaign Inputs","description":"What the messages are: `use_case`, `message_samples` and `opt_in_method` are the three the platform checks for before it considers the inputs complete."}},"type":"object","title":"A2pRegisterRequest","description":"Brand and campaign details for A2P 10DLC registration.\n\nMirrors `phone_numbers.interfaces.fastapi.dtos.A2pRegisterRequest`.\n\nBoth dicts are OPEN and forwarded as-is, matching the app, which types\nthem as bare `Dict[str, Any]` and stores them in JSONB before handing them\nto the carrier registry by name. Closing them here would reject a field\nthe registry added last week."},"AIBatchEnrichmentRequest":{"properties":{"list_id":{"type":"integer","title":"List Id"},"group_id":{"type":"string","title":"Group Id"},"record_ids":{"anyOf":[{"items":{"anyOf":[{"type":"integer"},{"type":"string"},{"type":"string","format":"uuid"}]},"type":"array"},{"type":"null"}],"title":"Record Ids"},"filter":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Filter","description":"Accepted; not applied by dispatch."},"enrichment_mode":{"type":"string","enum":["specific","all"],"title":"Enrichment Mode","default":"specific"},"usecase":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Usecase"},"model":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Model"},"allow_credit_deduction":{"type":"boolean","title":"Allow Credit Deduction","description":"Accepted; not applied by dispatch.","default":true},"dry_run":{"type":"boolean","title":"Dry Run","default":false},"priority":{"type":"integer","maximum":100.0,"minimum":0.0,"title":"Priority","description":"Accepted; not applied by dispatch.","default":0},"skip_existing_values":{"type":"boolean","title":"Skip Existing Values","default":false},"skip_recently_enriched":{"type":"boolean","title":"Skip Recently Enriched","default":true}},"type":"object","required":["list_id","group_id"],"title":"AIBatchEnrichmentRequest","description":"Run a saved AI group over a list. CHARGES per record.\n\n`enrichment_mode: all` runs EVERY record in the list; `specific` runs only\n`record_ids`. `dry_run` returns the record count and price and dispatches\nnothing."},"AIColumnMappingDto":{"properties":{"output_field":{"type":"string","title":"Output Field"},"column_id":{"type":"string","title":"Column Id"},"column_name":{"type":"string","title":"Column Name"}},"type":"object","required":["output_field","column_id","column_name"],"title":"AIColumnMappingDto","description":"Where one output field lands."},"AIConfigDto":{"properties":{"auto_update":{"type":"boolean","title":"Auto Update","description":"Re-run when new data arrives. ONGOING SPEND when true.","default":true},"run_condition":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Run Condition"},"scope":{"anyOf":[{"type":"string","enum":["company","contact","combined"]},{"type":"null"}],"title":"Scope"},"use_advanced_search":{"type":"boolean","title":"Use Advanced Search","default":false},"use_json":{"type":"boolean","title":"Use Json","default":false},"list_routing":{"anyOf":[{"$ref":"#/components/schemas/ListRoutingDto"},{"type":"null"}]},"skip_existing_values":{"type":"boolean","title":"Skip Existing Values","description":"Skip rows that already have a value - the main cost control.","default":true},"skip_recently_enriched":{"type":"boolean","title":"Skip Recently Enriched","description":"Skip rows enriched in the last 30 days.","default":true},"mode":{"type":"string","enum":["standard","find_people"],"title":"Mode","default":"standard"},"find_people":{"anyOf":[{"$ref":"#/components/schemas/AIFindPeopleSettingsDto"},{"type":"null"}]}},"type":"object","title":"AIConfigDto","description":"Execution settings for an AI enrichment group."},"AIConfigSummary":{"properties":{"group_id":{"type":"string","title":"Group Id"},"name":{"type":"string","title":"Name"},"usecase":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Usecase","description":"Use-case identifier (e.g. \"web-research\", \"content-generation\")."},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"is_global":{"type":"boolean","title":"Is Global","default":false},"is_active":{"type":"boolean","title":"Is Active","default":true}},"type":"object","required":["group_id","name"],"title":"AIConfigSummary","description":"One saved AI enrichment config attached to (or global for) a list.\n\n`group_id` is the handle the worker uses to load the prompt, model and\noutput mapping. `usecase` lets the client predict credit cost via\nenrichment.constants.AI_USECASE_CREDITS (e.g. web-research = 3 credits/record)."},"AIConfigsResponse":{"properties":{"configs":{"items":{"$ref":"#/components/schemas/AIConfigSummary"},"type":"array","title":"Configs"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"count":{"type":"integer","title":"Count","default":0}},"type":"object","title":"AIConfigsResponse","description":"Paginated (by list_id filter) collection of AI enrichment configs."},"AIEnrichmentConfigDto":{"properties":{"id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Id"},"group_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Group Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"input_mapping":{"items":{"type":"string"},"type":"array","maxItems":100,"minItems":1,"title":"Input Mapping"},"prompt":{"type":"string","maxLength":20000,"minLength":1,"title":"Prompt"},"config":{"$ref":"#/components/schemas/AIConfigDto"},"model":{"type":"string","title":"Model"},"usecase":{"type":"string","title":"Usecase"},"output_format":{"type":"string","title":"Output Format","default":"fields"},"json_schema":{"anyOf":[{"additionalProperties":{"type":"string","enum":["string","number","boolean"]},"type":"object"},{"type":"null"}],"title":"Json Schema"},"outputs":{"items":{"$ref":"#/components/schemas/AIOutputFieldDto"},"type":"array","maxItems":50,"minItems":1,"title":"Outputs"},"column_mappings":{"items":{"$ref":"#/components/schemas/AIColumnMappingDto"},"type":"array","title":"Column Mappings"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"is_global":{"type":"boolean","title":"Is Global","default":true},"created_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created By"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"},"org_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Org Id"}},"type":"object","required":["input_mapping","prompt","config","model","usecase","outputs"],"title":"AIEnrichmentConfigDto","description":"A full AI enrichment group definition."},"AIFindPeopleSettingsDto":{"properties":{"max_people":{"type":"integer","maximum":25.0,"minimum":1.0,"title":"Max People","default":5},"destination_table_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Destination Table Id"},"destination_table_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Destination Table Name"},"export_mode":{"type":"string","enum":["auto","review"],"title":"Export Mode","description":"`auto` exports found contacts without a human step; `review` holds them.","default":"review"},"review_store":{"type":"string","const":"source_metadata","title":"Review Store","default":"source_metadata"}},"type":"object","title":"AIFindPeopleSettingsDto","description":"Find-people mode settings for an AI group."},"AIFormulaGenerateRequest":{"properties":{"prompt":{"type":"string","minLength":1,"title":"Prompt"},"fields":{"items":{"type":"string"},"type":"array","title":"Fields","description":"Hint only: fields are read from your data."},"outputType":{"type":"string","maxLength":50,"title":"Outputtype","description":"Hint for the output kind.","default":"text"},"sampleData":{"additionalProperties":true,"type":"object","title":"Sampledata"}},"type":"object","required":["prompt"],"title":"AIFormulaGenerateRequest","description":"Turn a plain-language description into a formula. One model call."},"AIFormulaPreviewRequest":{"properties":{"formula":{"type":"string","minLength":1,"title":"Formula"},"sampleData":{"items":{"additionalProperties":true,"type":"object"},"type":"array","minItems":1,"title":"Sampledata","description":"Up to 10 rows are evaluated."},"fields":{"items":{"type":"string"},"type":"array","title":"Fields"}},"type":"object","required":["formula","sampleData"],"title":"AIFormulaPreviewRequest","description":"Evaluate a formula over sample rows you supply. Local, no model call."},"AIFormulaValidateRequest":{"properties":{"formula":{"type":"string","minLength":1,"title":"Formula"}},"type":"object","required":["formula"],"title":"AIFormulaValidateRequest","description":"Check a formula's syntax and field references."},"AIOutputFieldDto":{"properties":{"name":{"type":"string","title":"Name"},"type":{"type":"string","title":"Type"}},"type":"object","required":["name","type"],"title":"AIOutputFieldDto","description":"One field the AI pass is asked to return."},"AIPipelineDraftRequest":{"properties":{"goal":{"type":"string","maxLength":2000,"minLength":10,"title":"Goal"},"prioritize_cost":{"type":"boolean","title":"Prioritize Cost","description":"Prefer cheaper steps when drafting.","default":true},"qualification_mode":{"type":"string","enum":["auto","required","skip"],"title":"Qualification Mode","default":"auto"}},"type":"object","required":["goal"],"title":"AIPipelineDraftRequest","description":"Draft an enrichment pipeline from a stated goal. Returns a draft only."},"AIReviewApplyRequest":{"properties":{"finding_ids":{"items":{"type":"string"},"type":"array","title":"Finding Ids"}},"type":"object","required":["finding_ids"],"title":"AIReviewApplyRequest","description":"Apply findings DETERMINISTICALLY. Spends nothing - no model runs."},"AIReviewFixWithAIRequest":{"properties":{"finding":{"additionalProperties":true,"type":"object","title":"Finding"},"brand_mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Brand Mode"}},"type":"object","required":["finding"],"title":"AIReviewFixWithAIRequest","description":"Send ONE finding to the edit engine. SPENDS CREDIT."},"AIReviewRequest":{"properties":{"deep":{"type":"boolean","title":"Deep","default":true}},"type":"object","title":"AIReviewRequest","description":"Run a review pass over the page. SPENDS CREDIT.\n\n`deep` defaults TRUE, matching the app - the deeper pass is the one worth\nrunning, and quietly defaulting to the cheap one here would make the same\ncall behave differently through the API than in Studio."},"AIRunConditionRequest":{"properties":{"prompt":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Prompt","description":"The rule in plain words."},"fields":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Fields","description":"Fields the expression may use."},"sampleData":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Sampledata","description":"One sample record."},"entityType":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entitytype","description":"'contacts' or 'companies'."}},"additionalProperties":true,"type":"object","title":"AIRunConditionRequest","description":"Describe in words when an enrichment should run; get back an expression.\n\nThe app takes a FREE DICT here, so this model takes one too rather than\nnarrowing below it - every field is optional and unknown keys are forwarded\nuntouched. Narrowing would refuse a body the browser accepts, which is the\nmirror image of the bug the strict models elsewhere in this file prevent."},"AbmRollupRequest":{"properties":{"company_ids":{"items":{"type":"integer"},"type":"array","maxItems":500,"title":"Company Ids","description":"Company ids, at most 500 per call - the app refuses more; chunk larger sets."},"days":{"type":"integer","title":"Days","description":"Look-back window in days.","default":30}},"type":"object","required":["company_ids"],"title":"AbmRollupRequest","description":"Intent totals for a named set of accounts."},"AcceptTouchesRequest":{"properties":{"candidates":{"items":{"$ref":"#/components/schemas/TouchCandidate"},"type":"array","maxItems":100,"title":"Candidates"}},"type":"object","required":["candidates"],"title":"AcceptTouchesRequest"},"AccountDealCreateRequest":{"properties":{"name":{"type":"string","title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"amount":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Amount"},"currency":{"type":"string","title":"Currency","default":"USD"},"stage":{"type":"string","title":"Stage","description":"Stage NAME, not id.","default":"discovery"},"stage_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage Id","description":"Stage id. Takes precedence over `stage`."},"pipeline_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Pipeline Id"},"products":{"items":{"type":"string"},"type":"array","title":"Products"},"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id","description":"Who owns the deal. Omit to take the app's default - an API key is an ORGANISATION credential, so there is no 'me' to fall back to."},"close_date":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Close Date"},"contact_ids":{"items":{"type":"string"},"type":"array","maxItems":100,"title":"Contact Ids"}},"type":"object","required":["name"],"title":"AccountDealCreateRequest","description":"Create a deal already attached to an account.\n\n`POST /deals` creates one standalone. This attaches it in the same call,\nwhich is the difference worth having: a two-step create leaves a window\nwhere the deal exists with no account."},"AccountPlanApplyRequest":{"properties":{"proposed_plan":{"items":{"$ref":"#/components/schemas/AccountPlanStep"},"type":"array","title":"Proposed Plan"},"trigger":{"type":"string","title":"Trigger","description":"What caused this (re)plan.","default":"manual"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"draft | active | paused | archived."},"rationale":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Rationale"},"instruction":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Instruction"}},"type":"object","title":"AccountPlanApplyRequest","description":"Persist the approved steps as a NEW plan version.\n\n`proposed_plan` must be non-empty: apply REPLACES the account's steps, so\nan empty proposal would blank the plan. The app answers 400 rather than\ndoing it, and this surface forwards that rather than second-guessing it."},"AccountPlanListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"AccountPlanListPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape."},"AccountPlanPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"AccountPlanPayload","description":"An open envelope for a plan, a context read or a committee result."},"AccountPlanPreviewRequest":{"properties":{"proposed_plan":{"items":{"$ref":"#/components/schemas/AccountPlanStep"},"type":"array","title":"Proposed Plan"},"instruction":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Instruction","description":"Free-text note echoed back with the diff."}},"type":"object","title":"AccountPlanPreviewRequest","description":"Diff a proposed plan against the current version. Persists NOTHING.\n\nIt also does not consume the signal-replanner cooldown, so a caller can\npreview as often as it likes before committing with `/plan/apply`."},"AccountPlanStep":{"properties":{"step_id":{"type":"string","title":"Step Id","description":"Caller-assigned id, stable across versions."},"contact_id":{"anyOf":[{},{"type":"null"}],"title":"Contact Id","description":"Committee member this step is aimed at."},"channel":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Channel"},"scheduled_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Scheduled At"},"why_now":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Why Now"},"draft_content":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Draft Content"},"approval_status":{"type":"string","enum":["pending","approved","rejected","edited"],"title":"Approval Status","default":"pending"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"}},"additionalProperties":true,"type":"object","required":["step_id"],"title":"AccountPlanStep","description":"One step in a plan: who to reach, on what channel, when, and why now.\n\n`extra=\"allow\"` mirrors the app's own model, which is also open - the step\nshape carries per-channel extras the desk adds as it learns new channels,\nand a closed mirror would DROP them on the way in rather than pass them\nthrough.\n\n`approval_status` is closed because it reaches a real `Literal` inside the\nhandler: a free value would raise there and escape as a 500 instead of a\n422 naming the four states."},"AccountPlanStepUpdateRequest":{"properties":{"action":{"type":"string","enum":["approve","reject","edit"],"title":"Action"},"draft_content":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Draft Content"},"scheduled_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Scheduled At"}},"type":"object","required":["action"],"title":"AccountPlanStepUpdateRequest","description":"Approve, reject or edit ONE step on the latest plan version.\n\n`action` is closed - it reaches a real `Literal` inside the handler.\n`draft_content` is what `edit` edits; sending it with `approve` or\n`reject` is accepted and ignored, exactly as the app treats it."},"AccountPlanUpsertRequest":{"properties":{"goal":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Goal"},"deep_research_summary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Deep Research Summary"},"buying_committee_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Buying Committee Id"},"buying_committee_members":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Buying Committee Members"},"current_plan":{"items":{"$ref":"#/components/schemas/AccountPlanStep"},"type":"array","title":"Current Plan"},"trigger":{"type":"string","title":"Trigger","description":"What caused this (re)plan.","default":"manual"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"draft | active | paused | archived."},"rationale":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Rationale","description":"Optional why-now, recorded in the trigger history."}},"type":"object","title":"AccountPlanUpsertRequest","description":"Create the account's plan, or REPLAN it.\n\nThere is no update: a replan inserts a new version and bumps\n`plan_version`. Prior versions stay readable through\n`/desk/accounts/{account_id}/plan/history`."},"AccountStakeholderOutreachRequest":{"properties":{"type":{"type":"string","enum":["email","linkedin","call_script"],"title":"Type","description":"What to draft for this stakeholder."}},"type":"object","required":["type"],"title":"AccountStakeholderOutreachRequest","description":"Mirrors `accounts.GenerateOutreachRequest`."},"ActionDescriptorDto":{"properties":{"name":{"type":"string","title":"Name"},"label":{"type":"string","title":"Label"},"description":{"type":"string","title":"Description","default":""},"params":{"items":{"$ref":"#/components/schemas/ActionParamDto"},"type":"array","title":"Params"},"irreversible":{"type":"boolean","title":"Irreversible","description":"Cannot be undone. Surfaced so a host can confirm before invoking.","default":false}},"type":"object","required":["name","label"],"title":"ActionDescriptorDto","description":"One action a page may invoke on one of its bound sources."},"ActionParamDto":{"properties":{"name":{"type":"string","title":"Name"},"label":{"type":"string","title":"Label"},"type":{"type":"string","title":"Type","description":"string | number | date | bool | enum | json"},"required":{"type":"boolean","title":"Required","default":false},"sensitivity":{"type":"string","title":"Sensitivity","description":"`pii` marks personal data, so a host can treat it accordingly","default":"none"}},"type":"object","required":["name","label","type"],"title":"ActionParamDto","description":"One argument an action accepts."},"ActivateEngagersRequest":{"properties":{"contact_ids":{"items":{"type":"integer"},"type":"array","minItems":1,"title":"Contact Ids"},"action":{"type":"string","enum":["add_to_list","enroll_sequence"],"title":"Action"},"destination_list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Destination List Id"},"destination_list_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Destination List Name"},"sequence_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Id"},"conflict_resolution":{"anyOf":[{"type":"string","enum":["add_all","skip_all","custom"]},{"type":"null"}],"title":"Conflict Resolution"},"include_warned_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Include Warned Ids"}},"type":"object","required":["contact_ids","action"],"title":"ActivateEngagersRequest"},"AdAIReviewRequest":{"properties":{"deep":{"type":"boolean","title":"Deep","default":false}},"type":"object","title":"AdAIReviewRequest","description":"Run a review pass over the creative. SPENDS CREDIT.\n\n`deep` defaults FALSE here and TRUE on the landing-page review. That\nasymmetry is the app's and is preserved rather than smoothed over: the two\npasses cost differently."},"AdBatchCreateRequest":{"properties":{"ads":{"items":{"$ref":"#/components/schemas/AdCreateRequest"},"type":"array","maxItems":20,"minItems":1,"title":"Ads"}},"additionalProperties":false,"type":"object","required":["ads"],"title":"AdBatchCreateRequest","description":"Add several ads at once — \"launch these four creatives as four ads\".\n\nPartial success is expected: one creative rejected on policy does not stop\nthe others, and the response reports each outcome separately."},"AdBatchCreateResponse":{"properties":{"campaign_id":{"type":"integer","title":"Campaign Id"},"platform":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Platform"},"requested":{"type":"integer","title":"Requested"},"succeeded":{"type":"integer","title":"Succeeded"},"failed":{"type":"integer","title":"Failed"},"status":{"type":"string","title":"Status","description":"ok | partial — never render success off a 200 alone"},"results":{"items":{"$ref":"#/components/schemas/AdBatchResultItem"},"type":"array","title":"Results"}},"type":"object","required":["campaign_id","requested","succeeded","failed","status","results"],"title":"AdBatchCreateResponse"},"AdBatchResultItem":{"properties":{"index":{"type":"integer","title":"Index"},"status":{"type":"string","title":"Status"},"ad":{"anyOf":[{"$ref":"#/components/schemas/AdResponse"},{"type":"null"}]},"error":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Error"}},"type":"object","required":["index","status"],"title":"AdBatchResultItem"},"AdCampaignResponse":{"properties":{"id":{"type":"integer","title":"Id"},"sync_config_id":{"type":"integer","title":"Sync Config Id"},"platform":{"type":"string","title":"Platform"},"name":{"type":"string","title":"Name"},"objective":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Objective"},"status":{"type":"string","title":"Status"},"daily_budget":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Daily Budget"},"currency":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Currency"},"start_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Start Date"},"end_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"End Date"},"platform_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Platform Campaign Id"},"google_campaign_subtype":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Google Campaign Subtype"},"ad_count":{"type":"integer","title":"Ad Count","description":"Number of live (non-archived) ads in this campaign","default":0},"launched_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Launched At"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"past_end_date":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Past End Date","description":"True when end_date is before today (UTC). Null when the campaign has no end date."},"status_note":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status Note","description":"Plain-language note when the stored status cannot be taken at face value, e.g. the end date has passed but the status still says pending. Null otherwise."}},"type":"object","required":["id","sync_config_id","platform","name","status"],"title":"AdCampaignResponse","description":"A launched paid-ad campaign.\n\nCreative fields are NOT published here even though they still exist on the\nunderlying row for backwards compatibility. They are attributes of an ad,\nnot of a campaign, and publishing them at campaign level would force either\na breaking change or a permanent duplicate representation once a campaign\nholds more than one ad. Read them from ``/ad-campaigns/{id}/ads``."},"AdCollection":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"AdCollection","description":"A list of ad-platform objects.\n\nA bare list from the app is surfaced as `items`; a named collection keeps\nits own key AND gains `items`, so a caller can page either shape without\nknowing which handler produced it."},"AdCreateRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Name"},"headline":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Headline"},"primary_text":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Primary Text"},"description":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Description"},"cta":{"anyOf":[{"type":"string","maxLength":50},{"type":"null"}],"title":"Cta"},"destination_url":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Destination Url"},"creative_image_url":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Creative Image Url"},"creative_image_url_square":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Creative Image Url Square"},"creative_image_url_portrait":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Creative Image Url Portrait"},"logo_image_url":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Logo Image Url"},"copy_assets":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Copy Assets"},"source_ad_creative_id":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Source Ad Creative Id"}},"additionalProperties":false,"type":"object","title":"AdCreateRequest","description":"Add one ad to a campaign.\n\nValid before launch (created with its siblings when the campaign launches)\nand after (pushed to the live campaign immediately). ``extra=\"forbid\"`` so a\nfield we never wired is a 422 rather than a silent success."},"AdCreativeChatEditRequest":{"properties":{"instruction":{"type":"string","maxLength":2000,"title":"Instruction"}},"type":"object","required":["instruction"],"title":"AdCreativeChatEditRequest","description":"A natural-language edit to one creative. SPENDS CREDIT - a model runs."},"AdListResponse":{"properties":{"campaign_id":{"type":"integer","title":"Campaign Id"},"platform":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Platform"},"count":{"type":"integer","title":"Count"},"ads":{"items":{"$ref":"#/components/schemas/AdResponse"},"type":"array","title":"Ads"}},"type":"object","required":["campaign_id","count","ads"],"title":"AdListResponse"},"AdPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"AdPayload","description":"One ad-platform object, or one handler response."},"AdResponse":{"properties":{"id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Id","description":"graph8 ad id, stable across creative replacements. Null only for a campaign launched before per-ad control, until its first read."},"campaign_id":{"type":"integer","title":"Campaign Id"},"slot_index":{"type":"integer","title":"Slot Index"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"status":{"type":"string","title":"Status","description":"draft | launching | active | paused | archived | failed"},"headline":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Headline"},"primary_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Primary Text"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"cta":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Cta"},"destination_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Destination Url"},"creative_image_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Creative Image Url"},"creative_image_url_square":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Creative Image Url Square"},"creative_image_url_portrait":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Creative Image Url Portrait"},"logo_image_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Logo Image Url"},"copy_assets":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Copy Assets","description":"Multi-asset copy, e.g. {rsa_headlines: [...], rsa_descriptions: [...]}"},"source_ad_creative_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Ad Creative Id","description":"The Studio creative this ad was built from, when it came from Studio"},"platform_ad_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Platform Ad Id","description":"Current platform handle. Changes when the creative is replaced."},"approval_nuance":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Approval Nuance"},"policy_topics":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Policy Topics"},"error_message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Error Message"},"launched_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Launched At"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"}},"type":"object","required":["campaign_id","slot_index","status"],"title":"AdResponse","description":"One ad inside a campaign — a creative slot.\n\n``id`` is graph8's, and it is stable: editing an ad almost always mints a new\nplatform ad (LinkedIn creatives are immutable, and on Google only Search/RSA\nis mutable in place), but the slot and its measurement history survive that.\nAddress an ad by this id, never by ``platform_ad_id``."},"AdStatusRequest":{"properties":{"status":{"type":"string","enum":["active","paused"],"title":"Status"}},"additionalProperties":false,"type":"object","required":["status"],"title":"AdStatusRequest","description":"Pause or resume one ad without touching its siblings or the campaign."},"AdUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Name"},"headline":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Headline"},"primary_text":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Primary Text"},"description":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Description"},"cta":{"anyOf":[{"type":"string","maxLength":50},{"type":"null"}],"title":"Cta"},"destination_url":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Destination Url"},"creative_image_url":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Creative Image Url"},"creative_image_url_square":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Creative Image Url Square"},"creative_image_url_portrait":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Creative Image Url Portrait"},"logo_image_url":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Logo Image Url"},"copy_assets":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Copy Assets"},"source_ad_creative_id":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Source Ad Creative Id"}},"additionalProperties":false,"type":"object","title":"AdUpdateRequest","description":"Edit one ad. Omitted fields are unchanged.\n\nOn a live campaign a creative change is applied as a REPLACE, because that\nis what the platforms permit. The response reports whether the platform ad\nwas replaced so a caller knows review and learning restarted."},"AdUpdateResponse":{"properties":{"ad":{"$ref":"#/components/schemas/AdResponse"},"changed":{"items":{"type":"string"},"type":"array","title":"Changed"},"replaced_platform_ad":{"type":"boolean","title":"Replaced Platform Ad","description":"True when the platform ad was recreated; review and learning restart"},"consequences":{"items":{"type":"string"},"type":"array","title":"Consequences","description":"policy_review | learning_reset"}},"type":"object","required":["ad","changed","replaced_platform_ad"],"title":"AdUpdateResponse"},"AddChannelItem":{"properties":{"channel_id":{"type":"integer","title":"Channel Id","description":"The sender's INTEGER id - a mailbox, number or account."},"channel_value":{"type":"string","title":"Channel Value","description":"Its address: the email, phone number or profile."},"channel_type":{"type":"string","enum":["SMTP","GMAIL","INBOXKIT","PHONE","LINKEDIN","LINKEDIN_NETRION","SMS","WHATSAPP"],"title":"Channel Type"},"channel_data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Channel Data"}},"type":"object","required":["channel_id","channel_value","channel_type"],"title":"AddChannelItem","description":"One sender to attach. Mirrors `AddChannelPayload` minus the client `id`."},"AddChannelsRequest":{"properties":{"channels":{"items":{"$ref":"#/components/schemas/AddChannelItem"},"type":"array","minItems":1,"title":"Channels"}},"type":"object","required":["channels"],"title":"AddChannelsRequest","description":"Attach senders to a sequence. Mirrors `AddChannelParams`."},"AddContactsToListRequest":{"properties":{"contact_ids":{"items":{"type":"integer"},"type":"array","title":"Contact Ids","description":"List of contact IDs to add"},"conflict_resolution":{"anyOf":[{"type":"string","enum":["add_all","skip_all","custom"]},{"type":"null"}],"title":"Conflict Resolution","description":"Required on retry after a 409 CONFLICT_REVIEW_REQUIRED response: 'add_all' adds ready + every warned contact, 'skip_all' adds only ready contacts, 'custom' adds ready + the ids in include_warned_ids. Blocked contacts are always excluded regardless of this value."},"include_warned_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Include Warned Ids","description":"With conflict_resolution='custom', the warned contact ids to also add."}},"type":"object","required":["contact_ids"],"title":"AddContactsToListRequest","description":"Request body for adding contacts to a list."},"AddDealsToListRequest":{"properties":{"deal_ids":{"items":{"type":"string"},"type":"array","title":"Deal Ids","description":"Deal ids (strings, unlike the others)."},"source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source","description":"Where the addition came from, for the audit trail."}},"type":"object","required":["deal_ids"],"title":"AddDealsToListRequest","description":"Put deals on a deals list.\n\nDeal ids are STRINGS here while contact, company, suppression and lead ids\nare integers. That is the app's own typing and it is mirrored rather than\nsmoothed over: coercing would make a mistyped id a silent miss."},"AddEngagersToListRequest":{"properties":{"platform":{"type":"string","enum":["x","linkedin","reddit","instagram","youtube"],"title":"Platform","default":"linkedin"},"post_external_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Post External Id","description":"Optional echo of the path id. The PATH value is authoritative."},"engagement_type":{"anyOf":[{"type":"string","enum":["comment","reaction"]},{"type":"null"}],"title":"Engagement Type","description":"Only commenters, or only reactors. Omit for both."},"audience_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience Id","description":"An existing graph8 list."},"audience_name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Audience Name","description":"Create a new graph8 list with this name."}},"type":"object","title":"AddEngagersToListRequest","description":"Turn the people who engaged with a post into a graph8 list.\n\nSupply `audience_id` to add to an existing list, or `audience_name` to\ncreate one. Contacts that do not exist yet are created as stubs."},"AddExternalDomainsRequest":{"properties":{"domains":{"items":{"type":"string"},"type":"array","title":"Domains","description":"Domains already owned outside graph8, e.g. ['acme.com']"}},"type":"object","required":["domains"],"title":"AddExternalDomainsRequest","description":"Register domains you already own elsewhere so they can be used for sending."},"AddGuestsRequest":{"properties":{"guests":{"items":{"type":"string"},"type":"array","maxItems":50,"minItems":1,"title":"Guests"}},"type":"object","required":["guests"],"title":"AddGuestsRequest"},"AddInterviewMemberRequest":{"properties":{"name":{"type":"string","minLength":1,"title":"Name"},"email":{"type":"string","minLength":1,"title":"Email"},"send_invite":{"type":"boolean","title":"Send Invite","description":"Send the invite email now. TRUE REACHES A REAL PERSON.","default":false}},"type":"object","required":["name","email"],"title":"AddInterviewMemberRequest","description":"Add someone to an interview round.\n\n`send_invite=true` EMAILS THAT PERSON immediately. It defaults to false, so\nadding a member is a plain write unless the caller asks for the mail."},"AddNoteRequest":{"properties":{"text":{"type":"string","title":"Text"}},"type":"object","required":["text"],"title":"AddNoteRequest"},"AddPostToSequenceRequest":{"properties":{"sequence_id":{"type":"string","title":"Sequence Id"},"platform":{"type":"string","enum":["x","linkedin","reddit","instagram","youtube"],"title":"Platform","default":"x"}},"type":"object","required":["sequence_id"],"title":"AddPostToSequenceRequest","description":"Enrol a post's author into a sequence.\n\nASYNCHRONOUS. This resolves the author to a contact and publishes an\nenrolment request; the sequencer picks it up afterwards. A 200 means the\nrequest was accepted, not that the person is enrolled."},"AddRowRequest":{"properties":{"job_type":{"type":"string","title":"Job Type"},"source_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Url"},"target_keyword":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Keyword"},"original_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Original Title"},"original_meta":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Original Meta"},"original_body":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Original Body"},"author_team_member_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Author Team Member Id"}},"type":"object","required":["job_type"],"title":"AddRowRequest","description":"Add one job to a grid. Spends nothing until the job is run."},"AddSequenceContactsRequest":{"properties":{"contact_ids":{"items":{"type":"integer"},"type":"array","title":"Contact Ids","description":"Contact IDs to add to the sequence"},"list_id":{"type":"integer","title":"List Id","description":"List ID the contacts belong to"}},"type":"object","required":["contact_ids","list_id"],"title":"AddSequenceContactsRequest"},"AddStepItem":{"properties":{"step_order":{"type":"integer","title":"Step Order","description":"Position in the sequence, 1-based."},"step_type":{"type":"string","enum":["PHONE","EMAIL","MANUAL_DIALER","HEYREACH","NETRION","SMS","WHATSAPP"],"title":"Step Type"},"input_type":{"type":"string","enum":["ON_DEMAND","AI_GENERATED_TEMPLATE","MANUAL_TEMPLATE"],"title":"Input Type"},"time_interval":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Time Interval","description":"Seconds after the previous step."},"step_data":{"additionalProperties":true,"type":"object","title":"Step Data","description":"The step's content, the same shape as `step_data` on `GET /sequences/{sequence_id}/steps`: `subject` / `body` for email, `message_body` for SMS and WhatsApp, the `linkedin_*` fields for LinkedIn, `instructions` for AI generation."}},"type":"object","required":["step_order","step_type","input_type","step_data"],"title":"AddStepItem","description":"One step to add. Mirrors `CreateStepPayload` minus the client `id`."},"AddStepsRequest":{"properties":{"steps":{"items":{"$ref":"#/components/schemas/AddStepItem"},"type":"array","minItems":1,"title":"Steps"}},"type":"object","required":["steps"],"title":"AddStepsRequest","description":"Append steps to a sequence. Mirrors `CreateStepParams`."},"AgencyProfileUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"legal_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Legal Name"},"bio":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bio"},"logo_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Logo Url"},"country_code":{"anyOf":[{"type":"string","maxLength":2,"minLength":2},{"type":"null"}],"title":"Country Code","description":"ISO 3166-1 alpha-2."},"website":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Website"}},"type":"object","title":"AgencyProfileUpdateRequest","description":"The agency's own About/branding. Only these six fields are writable.\n\nNever `status`, `owner_org_id`, `agency_profile_id` or `billing_email` -\nthose decide who gets paid and whether the agency exists."},"AgencyStatementCreateRequest":{"properties":{"engagement_id":{"type":"string","title":"Engagement Id"},"summary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Summary"},"activities":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Activities"},"currency":{"type":"string","maxLength":3,"title":"Currency","default":"USD"}},"additionalProperties":false,"type":"object","required":["engagement_id"],"title":"AgencyStatementCreateRequest","description":"Draft a statement for one of the agency's own reps.\n\nNarrower than the talent-side create: the agency never gets to send a period\nor an amount at all, so those fields are absent rather than ignored."},"AgencyStatementUpdateRequest":{"properties":{"summary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Summary"},"activities":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Activities"}},"additionalProperties":false,"type":"object","title":"AgencyStatementUpdateRequest"},"AgentApprovalReceipt":{"properties":{"id":{"type":"string","title":"Id"},"entity_type":{"type":"string","title":"Entity Type"},"entity_id":{"type":"string","title":"Entity Id"},"action":{"type":"string","title":"Action"},"contributed_by_user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contributed By User Id"},"contributed_by_role_at_time":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contributed By Role At Time"},"via_list_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Via List Id"},"via_sequence_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Via Sequence Id"},"via_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Via Campaign Id"},"via_import_batch_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Via Import Batch Id"},"via_api_key_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Via Api Key Id"},"metadata_json":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Metadata Json"}},"type":"object","required":["id","entity_type","entity_id","action"],"title":"AgentApprovalReceipt","description":"One signed provenance row attributed to an approval."},"AgentApprovalReceiptsResponse":{"properties":{"approval_id":{"type":"string","title":"Approval Id"},"receipts":{"items":{"$ref":"#/components/schemas/AgentApprovalReceipt"},"type":"array","title":"Receipts","description":"Empty rather than an error when the approval produced no receipts."}},"type":"object","required":["approval_id"],"title":"AgentApprovalReceiptsResponse"},"AgentApprovalResponse":{"properties":{"id":{"type":"string","title":"Id"},"work_item_id":{"type":"string","title":"Work Item Id"},"step_id":{"type":"string","title":"Step Id"},"risk_level":{"type":"string","title":"Risk Level"},"action_class":{"type":"string","title":"Action Class"},"summary":{"type":"string","title":"Summary"},"detail":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Detail"},"requested_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Requested At"},"decided_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Decided At"},"decided_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Decided By"},"decision":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Decision"},"decision_payload":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Decision Payload"},"plan_digest":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Plan Digest","description":"The plan this approval was bound to. Compare it to the run's current plan to tell an approval that still describes the work from one that has drifted."},"expires_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Expires At"},"is_expired":{"type":"boolean","title":"Is Expired","default":false},"snapshot_digest":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Snapshot Digest"}},"type":"object","required":["id","work_item_id","step_id","risk_level","action_class","summary"],"title":"AgentApprovalResponse","description":"One approval: the loop asking permission before a consequential step."},"AgentBenchListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"AgentBenchListPayload","description":"An open envelope for a LIST answer, so a bare list keeps its shape."},"AgentBenchPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"AgentBenchPayload","description":"An open envelope for one approval answer.\n\nOpen because an approval carries the plan digest it is bound to, its expiry\nand its provenance receipts, and that set has grown twice already. On a\nhuman-in-the-loop surface a dropped field is a guarantee the caller does not\nknow they lost."},"AgentCardConfirmationRequest":{"properties":{"state":{"type":"string","enum":["approved","edited","rejected"],"title":"State","description":"`approved` accepts the card as proposed, `edited` accepts it with your `edits`, `rejected` sends it back. Re-sending the same state is a no-op; a different state overwrites."},"note":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Note","description":"Why, in your words."},"edits":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Edits","description":"Per-field overrides for an `edited` card. The shape is the card's own and varies by card kind."}},"type":"object","required":["state"],"title":"AgentCardConfirmationRequest","description":"Mirror of `wow_confirm_router.WowConfirmRequest`."},"AgentChatRequest":{"properties":{"message":{"type":"string","maxLength":10000,"title":"Message","description":"What you say to the agent. Required unless you attach a file.","default":""},"session_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Session Id","description":"Continue this session. Omit to start a new one; the answer carries its `session_id`."},"client_turn_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Client Turn Id","description":"Your own id for this turn, so a retry is recognised as the same turn rather than said twice. Needs an existing `session_id`."},"attachment_ids":{"items":{"type":"string","maxLength":255,"minLength":1},"type":"array","maxItems":20,"title":"Attachment Ids","description":"Uploaded file ids to attach, each at most once."},"subject_account_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subject Account Id","description":"Bind a NEW session to this account. Ignored for an existing one."},"subject_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subject Campaign Id","description":"Bind a NEW session to this campaign. Ignored for an existing one."},"mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mode","description":"Bias the agent: `web_search`, `deep_thinking` or `research`. Left open, as the app leaves it: an unknown mode is ignored rather than refused."},"mentions":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Mentions","description":"@-mentions from `POST /agent/mention-search`, passed through as returned (`id`, `category`, `display_name`, ...)."},"page":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Page","description":"Where the user is in your product, so 'this' and 'here' resolve."}},"type":"object","title":"AgentChatRequest","description":"Mirror of `agent_runtime.interfaces.routers.chat_router.ChatRequest`."},"AgentConversationPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"AgentConversationPayload","description":"An open envelope for the app's answer.\n\nOpen because the chat answer (`kind`, `message`, `chips`, `sources`,\n`work_item_id`, ...) and the oversight feed (`approvals`, `blockers`,\n`autonomous_fixes`, `states`, `bounds`) are both still growing, and a\ndropped field on an agent surface is one the caller does not know they\nlost."},"AgentCreateRequest":{"properties":{"chat_bot_id":{"type":"string","title":"Chat Bot Id","description":"Owning chat bot id (UUID)."},"agent_id":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Agent Id","description":"Agent id from agent settings."},"agent_name":{"type":"string","maxLength":255,"minLength":1,"title":"Agent Name"},"url_filter":{"items":{"type":"string"},"type":"array","title":"Url Filter","description":"URL paths where this agent is active."},"active":{"type":"boolean","title":"Active","default":true},"default":{"type":"boolean","title":"Default","description":"Used when no URL filter matches.","default":false},"surface":{"anyOf":[{"type":"string","enum":["external","internal"]},{"type":"null"}],"title":"Surface"}},"type":"object","required":["chat_bot_id","agent_name"],"title":"AgentCreateRequest","description":"Map an AI agent onto the URLs it should answer on."},"AgentDocumentSearch":{"properties":{"query":{"type":"string","minLength":1,"title":"Query"},"top_k":{"type":"integer","maximum":50.0,"minimum":1.0,"title":"Top K","default":5}},"type":"object","required":["query"],"title":"AgentDocumentSearch","description":"voice binds `query` and `top_k` as FORM fields beside `org_id` and\n`agent_id`; the router re-encodes this body as form data."},"AgentPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"AgentPayload","description":"An open envelope for memory, evidence and the proactive opener.\n\nEach carries planner or analysis state that changes as the agent platform\ndoes. On an oversight surface a dropped field reads as an agent doing less\nthan it did, so nothing here is pinned."},"AgentRegressionRun":{"properties":{"triggered_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Triggered By","description":"Attribution; defaults to the key's identity."}},"type":"object","title":"AgentRegressionRun"},"AgentRunListResponse":{"properties":{"runs":{"items":{"$ref":"#/components/schemas/AgentRunResponse"},"type":"array","title":"Runs"},"total":{"type":"integer","title":"Total"}},"type":"object","required":["runs","total"],"title":"AgentRunListResponse"},"AgentRunResponse":{"properties":{"work_item_id":{"type":"string","title":"Work Item Id"},"session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Id"},"title":{"type":"string","title":"Title"},"agent_id":{"type":"string","title":"Agent Id"},"entry_point":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entry Point"},"status":{"type":"string","title":"Status"},"current_step":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Current Step"},"next_action":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Next Action"},"visibility":{"type":"string","title":"Visibility"},"credits_spent":{"type":"integer","title":"Credits Spent","default":0},"credit_budget":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Credit Budget"},"created_at":{"type":"string","title":"Created At"},"updated_at":{"type":"string","title":"Updated At"},"completed_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Completed At"}},"type":"object","required":["work_item_id","title","agent_id","status","visibility","created_at","updated_at"],"title":"AgentRunResponse","description":"One run. Identical shape whether read from the list or on its own."},"AgentSession":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mode","description":"Session mode, e.g. `general`."},"is_pinned":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Pinned"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated At"}},"additionalProperties":true,"type":"object","title":"AgentSession","description":"One agent chat session."},"AgentSessionCreateRequest":{"properties":{"mode":{"type":"string","title":"Mode","description":"Session mode.","default":"general"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title","description":"Optional title; the app derives one when omitted."},"messages":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Messages","description":"Optional seed messages to open the session with."}},"type":"object","title":"AgentSessionCreateRequest"},"AgentSessionListResponse":{"properties":{"sessions":{"items":{"$ref":"#/components/schemas/AgentSession"},"type":"array","title":"Sessions"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"AgentSessionListResponse","description":"Sessions owned by, or shared with, the principal behind the key."},"AgentSessionMessageRequest":{"properties":{"content":{"type":"string","maxLength":10000,"minLength":1,"title":"Content","description":"The message text."}},"type":"object","required":["content"],"title":"AgentSessionMessageRequest","description":"Mirror of `messages_router.PostMessageRequest`."},"AgentSessionPinRequest":{"properties":{"is_pinned":{"type":"boolean","title":"Is Pinned","description":"True to pin, false to unpin."}},"type":"object","required":["is_pinned"],"title":"AgentSessionPinRequest"},"AgentSessionRenameRequest":{"properties":{"title":{"type":"string","minLength":1,"title":"Title","description":"New title."}},"type":"object","required":["title"],"title":"AgentSessionRenameRequest"},"AgentSessionStatePayload":{"properties":{},"additionalProperties":true,"type":"object","title":"AgentSessionStatePayload","description":"An open envelope for a hydration or voice answer.\n\nOpen because session hydration returns the agent's STEPS as well as its\nmessages, and a step's `detail` is whatever the tool that produced it\nreported. That set grows with every tool the platform gains, and a pinned\nmirror would drop the detail of exactly the newest ones - which on a\ntranscript surface reads as the agent having done less than it did."},"AgentSessionUpdateRequest":{"properties":{"messages":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Messages"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"}},"type":"object","title":"AgentSessionUpdateRequest","description":"Both fields are optional; omit one to leave it untouched."},"AgentTestCaseCreate":{"properties":{"name":{"type":"string","maxLength":200,"minLength":1,"title":"Name"},"input_message":{"type":"string","minLength":1,"title":"Input Message","description":"The user turn under test."},"input_context":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Input Context","description":"Surrounding facts held constant (prior turns, contact, company)."},"channel":{"type":"string","enum":["chat","inbound","outbound"],"title":"Channel","description":"Selects the per-channel instructions.","default":"chat"},"expected_output":{"anyOf":[{},{"type":"null"}],"title":"Expected Output","description":"What the assertion compares against; a tool name or list for expects_tool."},"assertion_type":{"type":"string","enum":["exact","contains","not_contains","expects_tool","refuses","cites_collection","llm_judge"],"title":"Assertion Type","default":"contains"},"assertion_config":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Assertion Config","description":"Assertion options: target (resolved_instructions | tool_names | grounding_sources), case_sensitive, tool, collection_id, capability_tools, refusal_markers."},"created_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created By","description":"Attribution; defaults to the key's identity."}},"type":"object","required":["name","input_message"],"title":"AgentTestCaseCreate","description":"A saved evaluation case: the user turn under test and what must hold.\n\n`llm_judge` may be SAVED but is skipped by dry runs - a judge needs a real\ncompletion, and a dry run never calls a model."},"AgentTestCaseUpdate":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":200,"minLength":1},{"type":"null"}],"title":"Name"},"input_message":{"anyOf":[{"type":"string","minLength":1},{"type":"null"}],"title":"Input Message"},"input_context":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Input Context"},"channel":{"anyOf":[{"type":"string","enum":["chat","inbound","outbound"]},{"type":"null"}],"title":"Channel"},"expected_output":{"anyOf":[{},{"type":"null"}],"title":"Expected Output"},"assertion_type":{"anyOf":[{"type":"string","enum":["exact","contains","not_contains","expects_tool","refuses","cites_collection","llm_judge"]},{"type":"null"}],"title":"Assertion Type"},"assertion_config":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Assertion Config"}},"type":"object","title":"AgentTestCaseUpdate"},"AgentTestRun":{"properties":{"mode":{"anyOf":[{"type":"string","enum":["preview","dry_run"]},{"type":"null"}],"title":"Mode","description":"preview | dry_run - both resolve configuration only."},"test_case_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Test Case Id"},"input_message":{"anyOf":[{"type":"string","minLength":1},{"type":"null"}],"title":"Input Message"},"input_context":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Input Context"},"channel":{"anyOf":[{"type":"string","enum":["chat","inbound","outbound"]},{"type":"null"}],"title":"Channel"},"expected_output":{"anyOf":[{},{"type":"null"}],"title":"Expected Output"},"assertion_type":{"anyOf":[{"type":"string","enum":["exact","contains","not_contains","expects_tool","refuses","cites_collection","llm_judge"]},{"type":"null"}],"title":"Assertion Type"},"assertion_config":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Assertion Config"},"triggered_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Triggered By"}},"type":"object","title":"AgentTestRun","description":"One dry run. Exactly one source: `test_case_id` (a saved case) or\n`input_message` (ad-hoc). Never calls a model, never places a call, never\nsends a message - it resolves what the agent WOULD receive and reach for."},"AgentUpdateRequest":{"properties":{"chat_bot_id":{"type":"string","title":"Chat Bot Id","description":"Owning chat bot id (UUID)."},"agent_id":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Agent Id"},"agent_name":{"anyOf":[{"type":"string","maxLength":255,"minLength":1},{"type":"null"}],"title":"Agent Name"},"url_filter":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Url Filter"},"active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Active"},"default":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Default"},"surface":{"anyOf":[{"type":"string","enum":["external","internal"]},{"type":"null"}],"title":"Surface"},"expected_revision":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Expected Revision"}},"type":"object","required":["chat_bot_id"],"title":"AgentUpdateRequest","description":"Partial edit of an agent mapping. `chat_bot_id` stays required.\n\nIt is not a field being changed - it is how the app FINDS the row, because\nagent ids are unique per bot rather than per org."},"AgentWorkItem":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"work_item_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Work Item Id"},"agent_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent Id"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"goal":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Goal"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"visibility":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Visibility"},"session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Id"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated At"}},"additionalProperties":true,"type":"object","title":"AgentWorkItem","description":"One unit of autonomous work."},"AgentWorkItemCreateRequest":{"properties":{"agent_id":{"type":"string","title":"Agent Id","description":"Which agent owns it. A known id the planner has a template for - `onboarding`, `dialer_setup`, `sequencer_setup`, `campaign_run`, `voice_setup`, `marketplace`, `dev_setup` - or a free-form value, for which the planner falls back to its `full` template. Left as an open string for that reason: an enum here would reject the ad-hoc case the planner explicitly supports."},"title":{"type":"string","maxLength":500,"minLength":1,"title":"Title"},"goal":{"type":"string","minLength":1,"title":"Goal","description":"What the agent should achieve."},"visibility":{"type":"string","enum":["shared","private"],"title":"Visibility","description":"`private` (default) or `shared` org-wide. The default is the safe one: work started through an API key is not visible to the whole org unless asked for.","default":"private"},"entry_point":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entry Point","description":"Per-session override. Unset, the planner reads the org's own signup entry point as the long-term truth - so omitting this is usually right."},"subject_account_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subject Account Id","description":"Bind the session to a company."},"subject_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subject Campaign Id","description":"Bind the session to a campaign."},"session_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Title","description":"Sidebar title. Defaults to `title`."},"seed_message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Seed Message","description":"First user message, so the session opens on the real request."},"skill_mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Skill Mode","description":"`web_search`, `deep_thinking` or `research`. Biases the planner prompt and model tier. Unknown values are IGNORED by the planner rather than rejected, which is why this is not an enum."},"page":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Page"},"source":{"anyOf":[{"type":"string","enum":["canvas","bridge"]},{"type":"null"}],"title":"Source"},"platform":{"anyOf":[{"type":"string","enum":["whatsapp","slack","roam","imessage"]},{"type":"null"}],"title":"Platform"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email","description":"Whose work item this is. Defaults to the identity the key was minted under."}},"type":"object","required":["agent_id","title","goal"],"title":"AgentWorkItemCreateRequest","description":"Start a unit of autonomous work."},"AgentWorkItemList":{"properties":{"work_items":{"items":{"$ref":"#/components/schemas/AgentWorkItem"},"type":"array","title":"Work Items"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"AgentWorkItemList"},"AgentWorkItemSteerRequest":{"properties":{"client_turn_id":{"type":"string","format":"uuid","title":"Client Turn Id","description":"Caller-generated idempotency key. REQUIRED, and the reason steering is safe to retry: the same id twice comes back `duplicate` rather than queueing a second instruction into a running agent."},"instruction":{"type":"string","maxLength":2000,"minLength":1,"title":"Instruction","description":"What to do differently. Applied at the next safe step boundary, not mid-step."}},"additionalProperties":false,"type":"object","required":["client_turn_id","instruction"],"title":"AgentWorkItemSteerRequest","description":"Redirect a RUNNING work item at its next safe step boundary.\n\n`extra=\"forbid\"` mirrors the app: an unknown key here is a typo in an\ninstruction payload, and dropping it silently would let a caller believe\nthey had steered when they had not."},"AiConnectionBlockRequest":{"properties":{"client_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Client Key","description":"Only this client. Omit to block every client."},"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason"}},"type":"object","title":"AiConnectionBlockRequest"},"AiConnectionsConfigRequest":{"properties":{"capture_detail":{"type":"boolean","title":"Capture Detail","description":"Record call inputs/outputs, not just counts.","default":true},"retention_days":{"type":"integer","enum":[30,90,365],"title":"Retention Days","default":90}},"type":"object","title":"AiConnectionsConfigRequest"},"AiDraftGenerateRequest":{"properties":{"conversation_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Conversation Id","description":"Ground the draft in this thread's history."},"channel_type":{"anyOf":[{"type":"string","enum":["email","heyreach","sms"]},{"type":"null"}],"title":"Channel Type","description":"Required alongside `conversation_id`. `heyreach` is the LinkedIn channel and additionally needs `linkedin_account_id`."},"linkedin_account_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Linkedin Account Id"},"message_html":{"type":"string","title":"Message Html","description":"The text to transform. Required by every operation except `generate_from_scratch`.","default":""},"operation":{"anyOf":[{"type":"string","enum":["change_tone","fix_grammar_spelling","change_objective","expand","shorten","change_persona","generate_from_scratch"]},{"items":{"type":"string","enum":["change_tone","fix_grammar_spelling","change_objective","expand","shorten","change_persona","generate_from_scratch"]},"type":"array"}],"title":"Operation","description":"One operation, or several applied together in a single charged call."},"tone":{"anyOf":[{"type":"string","enum":["professional","friendly","casual","assertive","empathetic","urgent"]},{"type":"null"}],"title":"Tone"},"objective":{"anyOf":[{"type":"string","enum":["book_meeting","follow_up","re_engage","provide_value","handle_objection","close_deal"]},{"type":"null"}],"title":"Objective"},"persona":{"anyOf":[{"type":"string","enum":["sdr","growth_manager","account_executive","customer_success","founder"]},{"type":"null"}],"title":"Persona"},"instructions":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Instructions","description":"Free-text prompt. With `generate_from_scratch` this writes a message with no thread at all."}},"type":"object","required":["operation"],"title":"AiDraftGenerateRequest","description":"Ask the model to write or rewrite a message. THIS SPENDS CREDITS.\n\nOne charge per call, including a multi-operation call: pass a LIST in\n`operation` to apply several transforms in a single generation rather than\npaying for each.\n\nNothing here is delivered anywhere - it returns text. Sending it is a\nseparate call."},"AiPauseRequest":{"properties":{"paused":{"type":"boolean","title":"Paused","description":"True stops the AI answering this thread; false lets it resume."}},"type":"object","required":["paused"],"title":"AiPauseRequest","description":"Stop or resume the AI auto-responder on ONE conversation.\n\nScoped to the conversation, not the org: pausing here does not disable the\nresponder anywhere else."},"AllTarget":{"properties":{"kind":{"type":"string","const":"all","title":"Kind","default":"all"}},"additionalProperties":false,"type":"object","title":"AllTarget","description":"Every record behind the report (the totals row)."},"Allocate":{"properties":{"statement_id":{"type":"string","format":"uuid","title":"Statement Id"}},"additionalProperties":false,"type":"object","required":["statement_id"],"title":"Allocate"},"AnalyticsMeta":{"properties":{"org_id":{"type":"string","title":"Org Id"},"days":{"type":"integer","title":"Days"},"cached":{"type":"boolean","title":"Cached"},"stale":{"type":"boolean","title":"Stale","default":false},"cache_ttl":{"type":"integer","title":"Cache Ttl","default":60},"timestamp":{"type":"string","format":"date-time","title":"Timestamp"},"query_time_ms":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Query Time Ms"}},"type":"object","required":["org_id","days","cached","timestamp"],"title":"AnalyticsMeta","description":"Metadata for analytics responses."},"AnalyticsResponse":{"properties":{"success":{"type":"boolean","title":"Success","default":true},"data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"items":{},"type":"array"}],"title":"Data"},"meta":{"$ref":"#/components/schemas/AnalyticsMeta"}},"type":"object","required":["data","meta"],"title":"AnalyticsResponse","description":"Standard analytics response wrapper."},"AnalyzeGapsRequest":{"properties":{"lenses":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Lenses"}},"type":"object","title":"AnalyzeGapsRequest"},"ApiHealthResponse":{"properties":{"status":{"type":"string","title":"Status","description":"Always 'ok' when the Developer API is serving requests.","default":"ok"},"service":{"type":"string","title":"Service","description":"Which service answered. Always 'developer-api'.","default":"developer-api"}},"type":"object","title":"ApiHealthResponse"},"ApiKeyCreateRequest":{"properties":{"name":{"type":"string","maxLength":100,"minLength":1,"title":"Name","description":"Human-readable name for the key"},"expires_in_days":{"anyOf":[{"type":"integer","maximum":365.0,"minimum":1.0},{"type":"null"}],"title":"Expires In Days","description":"Days until key expires (optional)"},"mode":{"type":"string","enum":["live","test","sandbox"],"title":"Mode","description":"Key mode. A 'test' key is returned with a g8_test_ prefix; a 'live' key carries g8_live_; a 'sandbox' key carries g8_sbx_ and only authenticates against the graph8 developer sandbox. A key minted by a 'test'-mode credential is always forced to 'test' regardless of this field — a test key may not mint itself a live successor.","default":"live"},"scopes":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Scopes","description":"Restrict the new key to specific resource:action scopes (e.g. ['contacts:read', 'deals:*']). '*' grants everything; 'resource:*' grants every action on a resource. Omitted or empty grants the full current scope vocabulary (today's status quo for an unscoped key), stored explicitly so the key stays narrowable and auditable rather than permanently unrestricted."},"ip_allowlist":{"items":{"type":"string"},"type":"array","title":"Ip Allowlist","description":"Optional list of IPv4/IPv6 CIDR strings (e.g. ['10.0.0.0/8', '2001:db8::/32']). Bare IPs are accepted as /32 (IPv4) or /128 (IPv6). When non-empty, only requests from a matching IP are accepted — all others receive 403. Empty list (the default) means unrestricted: the key works from any IP address. Maximum 50 entries."}},"additionalProperties":false,"type":"object","required":["name"],"title":"ApiKeyCreateRequest","description":"Request to mint a new organization API key.\n\n``extra=\"forbid\"`` so a caller sending ``org_id``, ``is_agency`` or\n``is_ops`` gets an explicit 422 instead of the field being silently\ndropped — it is a stronger, more debuggable signal that those fields do\nnot exist on this door."},"ApiKeyCreateResponse":{"properties":{"api_key_id":{"type":"string","title":"Api Key Id"},"api_key_token":{"type":"string","title":"Api Key Token"},"name":{"type":"string","title":"Name"},"mode":{"type":"string","title":"Mode","default":"live"},"scopes":{"items":{"type":"string"},"type":"array","title":"Scopes"}},"type":"object","required":["api_key_id","api_key_token","name"],"title":"ApiKeyCreateResponse","description":"Response after minting a key.\n\n``api_key_token`` is returned exactly once, here, at creation. No other\nendpoint on this router — or the app's — ever returns it again."},"ApiKeyIpAllowlistRequest":{"properties":{"ip_allowlist":{"items":{"type":"string"},"type":"array","title":"Ip Allowlist","description":"Replacement list of CIDR strings. Pass [] to remove all restrictions. Maximum 50 entries."}},"additionalProperties":false,"type":"object","required":["ip_allowlist"],"title":"ApiKeyIpAllowlistRequest","description":"Request body to replace an existing key's IP allowlist in-place."},"ApiKeyListResponse":{"properties":{"keys":{"items":{"$ref":"#/components/schemas/ApiKeyResponse"},"type":"array","title":"Keys"},"total":{"type":"integer","title":"Total"}},"type":"object","required":["keys","total"],"title":"ApiKeyListResponse"},"ApiKeyResponse":{"properties":{"api_key_id":{"type":"string","title":"Api Key Id"},"name":{"type":"string","title":"Name"},"created_at":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Created At"},"expires_at":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Expires At"},"is_agency":{"type":"boolean","title":"Is Agency","description":"Whether this key is agency-scoped. Informational — this door cannot mint one.","default":false},"mode":{"type":"string","title":"Mode","default":"live"},"last_used_at":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Last Used At"},"scopes":{"items":{"type":"string"},"type":"array","title":"Scopes"},"is_legacy_unrestricted":{"type":"boolean","title":"Is Legacy Unrestricted","description":"True for a key minted before scopes existed. An empty scope list means unrestricted, not 'no access'.","default":false},"created_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created By"},"ip_allowlist":{"items":{"type":"string"},"type":"array","title":"Ip Allowlist","description":"CIDRs this key is restricted to. Empty = unrestricted."},"daily_credit_cap":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Daily Credit Cap","description":"Daily spending cap in credits. Null = no daily cap."},"monthly_credit_cap":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Monthly Credit Cap","description":"Monthly spending cap in credits. Null = no monthly cap."},"spend_alert_threshold_pct":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Spend Alert Threshold Pct","description":"Percent of a cap at which the key owner is alerted. Null when no cap is set."}},"type":"object","required":["api_key_id","name"],"title":"ApiKeyResponse","description":"One API key's metadata (never the secret)."},"ApiKeyRotateRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":100,"minLength":1},{"type":"null"}],"title":"Name"},"expires_in_days":{"anyOf":[{"type":"integer","maximum":365.0,"minimum":1.0},{"type":"null"}],"title":"Expires In Days"},"ip_allowlist":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Ip Allowlist","description":"Update the IP allowlist on rotation. Omit to preserve the existing allowlist. Pass [] to remove all restrictions."}},"additionalProperties":false,"type":"object","title":"ApiKeyRotateRequest","description":"Request to rotate a key. Mode, scopes and agency status are preserved\nfrom the key being rotated — none are settable here.\n\n``ip_allowlist`` is settable on rotation: a rotation is the natural moment\nto update network restrictions alongside the new credential.\nWhen omitted the old key's allowlist is preserved."},"ApiKeySpendCapsRequest":{"properties":{"daily_credit_cap":{"anyOf":[{"type":"integer","maximum":100000000.0,"minimum":1.0},{"type":"null"}],"title":"Daily Credit Cap","description":"Daily cap in credits, resetting 00:00 UTC; null = no daily cap."},"monthly_credit_cap":{"anyOf":[{"type":"integer","maximum":100000000.0,"minimum":1.0},{"type":"null"}],"title":"Monthly Credit Cap","description":"Monthly cap in credits, resetting on the 1st; null = no monthly cap."},"spend_alert_threshold_pct":{"anyOf":[{"type":"integer","maximum":100.0,"minimum":1.0},{"type":"null"}],"title":"Spend Alert Threshold Pct","description":"Alert the key owner at this percent of a cap. Defaults to 80 when a cap is set."}},"additionalProperties":false,"type":"object","title":"ApiKeySpendCapsRequest","description":"Replace a key's spending caps in place. A FULL replace: resend any value you want to keep.\n\nA cap is in credits and bounds only the BILLABLE operations that key makes: once the key's spend for the current UTC\nday (or month) would pass it, the next billable call is refused with 402. `null` removes that window's cap."},"ApiKeySpendResponse":{"properties":{"api_key_id":{"type":"string","title":"Api Key Id"},"daily_credit_cap":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Daily Credit Cap"},"monthly_credit_cap":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Monthly Credit Cap"},"spend_alert_threshold_pct":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Spend Alert Threshold Pct"},"daily_spent":{"type":"integer","title":"Daily Spent","default":0},"monthly_spent":{"type":"integer","title":"Monthly Spent","default":0},"daily_remaining":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Daily Remaining","description":"Credits left today; null when there is no daily cap."},"monthly_remaining":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Monthly Remaining","description":"Credits left this month; null when there is no monthly cap."}},"type":"object","required":["api_key_id"],"title":"ApiKeySpendResponse","description":"A key's caps beside what it has spent in the current UTC day and month."},"ApiResponse_AIConfigsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AIConfigsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AIConfigsResponse]"},"ApiResponse_AccountPlanListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/AccountPlanListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AccountPlanListPayload]"},"ApiResponse_AccountPlanPayload_":{"properties":{"data":{"$ref":"#/components/schemas/AccountPlanPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AccountPlanPayload]"},"ApiResponse_AdBatchCreateResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AdBatchCreateResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AdBatchCreateResponse]"},"ApiResponse_AdCampaignResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AdCampaignResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AdCampaignResponse]"},"ApiResponse_AdCollection_":{"properties":{"data":{"$ref":"#/components/schemas/AdCollection"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AdCollection]"},"ApiResponse_AdListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AdListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AdListResponse]"},"ApiResponse_AdPayload_":{"properties":{"data":{"$ref":"#/components/schemas/AdPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AdPayload]"},"ApiResponse_AdResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AdResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AdResponse]"},"ApiResponse_AdUpdateResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AdUpdateResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AdUpdateResponse]"},"ApiResponse_AgentApprovalReceiptsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AgentApprovalReceiptsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AgentApprovalReceiptsResponse]"},"ApiResponse_AgentApprovalResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AgentApprovalResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AgentApprovalResponse]"},"ApiResponse_AgentBenchListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/AgentBenchListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AgentBenchListPayload]"},"ApiResponse_AgentBenchPayload_":{"properties":{"data":{"$ref":"#/components/schemas/AgentBenchPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AgentBenchPayload]"},"ApiResponse_AgentConversationPayload_":{"properties":{"data":{"$ref":"#/components/schemas/AgentConversationPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AgentConversationPayload]"},"ApiResponse_AgentPayload_":{"properties":{"data":{"$ref":"#/components/schemas/AgentPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AgentPayload]"},"ApiResponse_AgentRunListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AgentRunListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AgentRunListResponse]"},"ApiResponse_AgentRunResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AgentRunResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AgentRunResponse]"},"ApiResponse_AgentSessionListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AgentSessionListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AgentSessionListResponse]"},"ApiResponse_AgentSessionStatePayload_":{"properties":{"data":{"$ref":"#/components/schemas/AgentSessionStatePayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AgentSessionStatePayload]"},"ApiResponse_AgentSession_":{"properties":{"data":{"$ref":"#/components/schemas/AgentSession"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AgentSession]"},"ApiResponse_AgentWorkItemList_":{"properties":{"data":{"$ref":"#/components/schemas/AgentWorkItemList"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AgentWorkItemList]"},"ApiResponse_AgentWorkItem_":{"properties":{"data":{"$ref":"#/components/schemas/AgentWorkItem"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AgentWorkItem]"},"ApiResponse_Any_":{"properties":{"data":{"title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[Any]"},"ApiResponse_ApiKeyCreateResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ApiKeyCreateResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ApiKeyCreateResponse]"},"ApiResponse_ApiKeyListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ApiKeyListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ApiKeyListResponse]"},"ApiResponse_ApiKeyResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ApiKeyResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ApiKeyResponse]"},"ApiResponse_ApiKeySpendResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ApiKeySpendResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ApiKeySpendResponse]"},"ApiResponse_AppLimitResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AppLimitResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppLimitResponse]"},"ApiResponse_AppLogsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AppLogsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppLogsResponse]"},"ApiResponse_AppPageActionsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AppPageActionsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppPageActionsResponse]"},"ApiResponse_AppPageArtifactResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AppPageArtifactResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppPageArtifactResponse]"},"ApiResponse_AppPageChatEditResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AppPageChatEditResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppPageChatEditResponse]"},"ApiResponse_AppPageFrameSessionResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AppPageFrameSessionResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppPageFrameSessionResponse]"},"ApiResponse_AppPageResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AppPageResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppPageResponse]"},"ApiResponse_AppPageRestoreResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AppPageRestoreResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppPageRestoreResponse]"},"ApiResponse_AppPageSourceCatalogPayload_":{"properties":{"data":{"$ref":"#/components/schemas/AppPageSourceCatalogPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppPageSourceCatalogPayload]"},"ApiResponse_AppPageSourcesPayload_":{"properties":{"data":{"$ref":"#/components/schemas/AppPageSourcesPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppPageSourcesPayload]"},"ApiResponse_AppPageStatusResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AppPageStatusResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppPageStatusResponse]"},"ApiResponse_AppPageVersionListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AppPageVersionListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppPageVersionListResponse]"},"ApiResponse_AppResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AppResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppResponse]"},"ApiResponse_AppRuntimeResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AppRuntimeResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppRuntimeResponse]"},"ApiResponse_AppSecretResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AppSecretResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppSecretResponse]"},"ApiResponse_AppUserResponsesDTO_":{"properties":{"data":{"$ref":"#/components/schemas/AppUserResponsesDTO"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppUserResponsesDTO]"},"ApiResponse_ApplyManifestResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ApplyManifestResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ApplyManifestResponse]"},"ApiResponse_ApplyResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ApplyResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ApplyResponse]"},"ApiResponse_AppointmentHostGroup_":{"properties":{"data":{"$ref":"#/components/schemas/AppointmentHostGroup"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppointmentHostGroup]"},"ApiResponse_AppointmentHost_":{"properties":{"data":{"$ref":"#/components/schemas/AppointmentHost"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppointmentHost]"},"ApiResponse_AppointmentLimitsPayload_":{"properties":{"data":{"$ref":"#/components/schemas/AppointmentLimitsPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AppointmentLimitsPayload]"},"ApiResponse_AttributeDefinitionResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AttributeDefinitionResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AttributeDefinitionResponse]"},"ApiResponse_AudiencePipelineAcceptResult_":{"properties":{"data":{"$ref":"#/components/schemas/AudiencePipelineAcceptResult"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AudiencePipelineAcceptResult]"},"ApiResponse_AudiencePipelineStatus_":{"properties":{"data":{"$ref":"#/components/schemas/AudiencePipelineStatus"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AudiencePipelineStatus]"},"ApiResponse_AudiencePipelineSuggestedFilters_":{"properties":{"data":{"$ref":"#/components/schemas/AudiencePipelineSuggestedFilters"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AudiencePipelineSuggestedFilters]"},"ApiResponse_AudiencePipelineTriggerResult_":{"properties":{"data":{"$ref":"#/components/schemas/AudiencePipelineTriggerResult"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AudiencePipelineTriggerResult]"},"ApiResponse_AudienceSyncConfigResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AudienceSyncConfigResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AudienceSyncConfigResponse]"},"ApiResponse_AuditLogResponse_":{"properties":{"data":{"$ref":"#/components/schemas/AuditLogResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[AuditLogResponse]"},"ApiResponse_BackupDownloadResponse_":{"properties":{"data":{"$ref":"#/components/schemas/BackupDownloadResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[BackupDownloadResponse]"},"ApiResponse_BackupJobListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/BackupJobListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[BackupJobListResponse]"},"ApiResponse_BackupJobResponse_":{"properties":{"data":{"$ref":"#/components/schemas/BackupJobResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[BackupJobResponse]"},"ApiResponse_BatchAssertResponse_":{"properties":{"data":{"$ref":"#/components/schemas/BatchAssertResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[BatchAssertResponse]"},"ApiResponse_BillingListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/BillingListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[BillingListPayload]"},"ApiResponse_BillingPayload_":{"properties":{"data":{"$ref":"#/components/schemas/BillingPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[BillingPayload]"},"ApiResponse_BugReportListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/BugReportListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[BugReportListPayload]"},"ApiResponse_BugReportPayload_":{"properties":{"data":{"$ref":"#/components/schemas/BugReportPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[BugReportPayload]"},"ApiResponse_BulkReinstateResponse_":{"properties":{"data":{"$ref":"#/components/schemas/BulkReinstateResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[BulkReinstateResponse]"},"ApiResponse_BulkSuppressResponse_":{"properties":{"data":{"$ref":"#/components/schemas/BulkSuppressResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[BulkSuppressResponse]"},"ApiResponse_CalendarInvitePayload_":{"properties":{"data":{"$ref":"#/components/schemas/CalendarInvitePayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CalendarInvitePayload]"},"ApiResponse_CallGradingResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CallGradingResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CallGradingResponse]"},"ApiResponse_CallTranscriptResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CallTranscriptResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CallTranscriptResponse]"},"ApiResponse_CallsListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CallsListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CallsListResponse]"},"ApiResponse_CampaignVisitorsReport_":{"properties":{"data":{"$ref":"#/components/schemas/CampaignVisitorsReport"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CampaignVisitorsReport]"},"ApiResponse_CampaignWorkflowListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/CampaignWorkflowListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CampaignWorkflowListPayload]"},"ApiResponse_CampaignWorkflowPayload_":{"properties":{"data":{"$ref":"#/components/schemas/CampaignWorkflowPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CampaignWorkflowPayload]"},"ApiResponse_CancelAgentRunResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CancelAgentRunResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CancelAgentRunResponse]"},"ApiResponse_ClickhouseMashupResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ClickhouseMashupResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ClickhouseMashupResponse]"},"ApiResponse_ClickhouseOrgAnalyticsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ClickhouseOrgAnalyticsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ClickhouseOrgAnalyticsResponse]"},"ApiResponse_CloseReasonListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CloseReasonListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CloseReasonListResponse]"},"ApiResponse_CoachListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/CoachListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CoachListPayload]"},"ApiResponse_CoachPayload_":{"properties":{"data":{"$ref":"#/components/schemas/CoachPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CoachPayload]"},"ApiResponse_ColumnFillRatesResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ColumnFillRatesResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ColumnFillRatesResponse]"},"ApiResponse_CompanyAssertResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CompanyAssertResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CompanyAssertResponse]"},"ApiResponse_CompanyCreateResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CompanyCreateResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CompanyCreateResponse]"},"ApiResponse_CompanyNpsDTO_":{"properties":{"data":{"$ref":"#/components/schemas/CompanyNpsDTO"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CompanyNpsDTO]"},"ApiResponse_CompanyResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CompanyResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CompanyResponse]"},"ApiResponse_ComputedStateResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ComputedStateResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ComputedStateResponse]"},"ApiResponse_ComputedStatusResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ComputedStatusResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ComputedStatusResponse]"},"ApiResponse_ConnectionListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/ConnectionListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ConnectionListPayload]"},"ApiResponse_ConnectionPayload_":{"properties":{"data":{"$ref":"#/components/schemas/ConnectionPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ConnectionPayload]"},"ApiResponse_ContactAssertResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ContactAssertResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ContactAssertResponse]"},"ApiResponse_ContactBrief_":{"properties":{"data":{"$ref":"#/components/schemas/ContactBrief"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ContactBrief]"},"ApiResponse_ContactBulkGetResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ContactBulkGetResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ContactBulkGetResponse]"},"ApiResponse_ContactCreateResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ContactCreateResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ContactCreateResponse]"},"ApiResponse_ContactHistoryDTO_":{"properties":{"data":{"$ref":"#/components/schemas/ContactHistoryDTO"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ContactHistoryDTO]"},"ApiResponse_ContactRelatedBatchResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ContactRelatedBatchResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ContactRelatedBatchResponse]"},"ApiResponse_ContactResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ContactResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ContactResponse]"},"ApiResponse_ContactSupportResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ContactSupportResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ContactSupportResponse]"},"ApiResponse_ContactTagListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ContactTagListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ContactTagListResponse]"},"ApiResponse_ContactTagWriteResult_":{"properties":{"data":{"$ref":"#/components/schemas/ContactTagWriteResult"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ContactTagWriteResult]"},"ApiResponse_ContactTag_":{"properties":{"data":{"$ref":"#/components/schemas/ContactTag"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ContactTag]"},"ApiResponse_ContentGridSkillPayload_":{"properties":{"data":{"$ref":"#/components/schemas/ContentGridSkillPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ContentGridSkillPayload]"},"ApiResponse_CopilotMemoryListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/CopilotMemoryListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CopilotMemoryListPayload]"},"ApiResponse_CopilotMemoryPayload_":{"properties":{"data":{"$ref":"#/components/schemas/CopilotMemoryPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CopilotMemoryPayload]"},"ApiResponse_CreateCompanyColumnResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CreateCompanyColumnResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CreateCompanyColumnResponse]"},"ApiResponse_CreateContactColumnResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CreateContactColumnResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CreateContactColumnResponse]"},"ApiResponse_CreateDefaultWaterfallConfigResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CreateDefaultWaterfallConfigResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CreateDefaultWaterfallConfigResponse]"},"ApiResponse_CreateFieldResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CreateFieldResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CreateFieldResponse]"},"ApiResponse_CreateFieldsBatchResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CreateFieldsBatchResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CreateFieldsBatchResponse]"},"ApiResponse_CreatedAgentRunResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CreatedAgentRunResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CreatedAgentRunResponse]"},"ApiResponse_CreatedAppPageResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CreatedAppPageResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CreatedAppPageResponse]"},"ApiResponse_CreatedCredentialResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CreatedCredentialResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CreatedCredentialResponse]"},"ApiResponse_CredentialResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CredentialResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CredentialResponse]"},"ApiResponse_CrmAudienceResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CrmAudienceResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CrmAudienceResponse]"},"ApiResponse_CrmCollectionPayload_":{"properties":{"data":{"$ref":"#/components/schemas/CrmCollectionPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CrmCollectionPayload]"},"ApiResponse_CrmCollection_":{"properties":{"data":{"$ref":"#/components/schemas/CrmCollection"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CrmCollection]"},"ApiResponse_CrmFieldsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CrmFieldsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CrmFieldsResponse]"},"ApiResponse_CrmMigrationReportPayload_":{"properties":{"data":{"$ref":"#/components/schemas/CrmMigrationReportPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CrmMigrationReportPayload]"},"ApiResponse_CrmObjectCatalogPayload_":{"properties":{"data":{"$ref":"#/components/schemas/CrmObjectCatalogPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CrmObjectCatalogPayload]"},"ApiResponse_CrmObjectFieldsPayload_":{"properties":{"data":{"$ref":"#/components/schemas/CrmObjectFieldsPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CrmObjectFieldsPayload]"},"ApiResponse_CrmObjectSyncPayload_":{"properties":{"data":{"$ref":"#/components/schemas/CrmObjectSyncPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CrmObjectSyncPayload]"},"ApiResponse_CrmPayload_":{"properties":{"data":{"$ref":"#/components/schemas/CrmPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CrmPayload]"},"ApiResponse_CrmPushResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CrmPushResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CrmPushResponse]"},"ApiResponse_CrmRecordPayload_":{"properties":{"data":{"$ref":"#/components/schemas/CrmRecordPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CrmRecordPayload]"},"ApiResponse_CrmReviewQueuePayload_":{"properties":{"data":{"$ref":"#/components/schemas/CrmReviewQueuePayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CrmReviewQueuePayload]"},"ApiResponse_CrmStatusResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CrmStatusResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CrmStatusResponse]"},"ApiResponse_CrmSyncRunPayload_":{"properties":{"data":{"$ref":"#/components/schemas/CrmSyncRunPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CrmSyncRunPayload]"},"ApiResponse_CsvExportPayload_":{"properties":{"data":{"$ref":"#/components/schemas/CsvExportPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CsvExportPayload]"},"ApiResponse_CustomFieldDiConfigListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CustomFieldDiConfigListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CustomFieldDiConfigListResponse]"},"ApiResponse_CustomObjectCapabilitiesResponse_":{"properties":{"data":{"$ref":"#/components/schemas/CustomObjectCapabilitiesResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[CustomObjectCapabilitiesResponse]"},"ApiResponse_DataFilePreviewResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DataFilePreviewResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DataFilePreviewResponse]"},"ApiResponse_DataFileUploadResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DataFileUploadResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DataFileUploadResponse]"},"ApiResponse_DataPipelineItems_":{"properties":{"data":{"$ref":"#/components/schemas/DataPipelineItems"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DataPipelineItems]"},"ApiResponse_DealAssertResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DealAssertResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DealAssertResponse]"},"ApiResponse_DealCollectionPayload_":{"properties":{"data":{"$ref":"#/components/schemas/DealCollectionPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DealCollectionPayload]"},"ApiResponse_DealContactListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DealContactListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DealContactListResponse]"},"ApiResponse_DealContact_":{"properties":{"data":{"$ref":"#/components/schemas/DealContact"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DealContact]"},"ApiResponse_DealDetail_":{"properties":{"data":{"$ref":"#/components/schemas/DealDetail"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DealDetail]"},"ApiResponse_DealLineItemsPayload_":{"properties":{"data":{"$ref":"#/components/schemas/DealLineItemsPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DealLineItemsPayload]"},"ApiResponse_DealListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DealListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DealListResponse]"},"ApiResponse_DealOpResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DealOpResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DealOpResponse]"},"ApiResponse_DealPayload_":{"properties":{"data":{"$ref":"#/components/schemas/DealPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DealPayload]"},"ApiResponse_DealResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DealResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DealResponse]"},"ApiResponse_DealStageVelocityPayload_":{"properties":{"data":{"$ref":"#/components/schemas/DealStageVelocityPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DealStageVelocityPayload]"},"ApiResponse_DealTouchSearchPayload_":{"properties":{"data":{"$ref":"#/components/schemas/DealTouchSearchPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DealTouchSearchPayload]"},"ApiResponse_DealTouchSettingsPayload_":{"properties":{"data":{"$ref":"#/components/schemas/DealTouchSettingsPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DealTouchSettingsPayload]"},"ApiResponse_DealTouchTimelinePayload_":{"properties":{"data":{"$ref":"#/components/schemas/DealTouchTimelinePayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DealTouchTimelinePayload]"},"ApiResponse_DeleteFieldResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DeleteFieldResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DeleteFieldResponse]"},"ApiResponse_DeliverabilityListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/DeliverabilityListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DeliverabilityListPayload]"},"ApiResponse_DeliverabilityPayload_":{"properties":{"data":{"$ref":"#/components/schemas/DeliverabilityPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DeliverabilityPayload]"},"ApiResponse_DependentsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DependentsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DependentsResponse]"},"ApiResponse_DeploymentResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DeploymentResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DeploymentResponse]"},"ApiResponse_DeskBatch_":{"properties":{"data":{"$ref":"#/components/schemas/DeskBatch"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DeskBatch]"},"ApiResponse_DeskCardResult_":{"properties":{"data":{"$ref":"#/components/schemas/DeskCardResult"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DeskCardResult]"},"ApiResponse_DeskDecisionListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DeskDecisionListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DeskDecisionListResponse]"},"ApiResponse_DeskListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/DeskListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DeskListPayload]"},"ApiResponse_DeskPayload_":{"properties":{"data":{"$ref":"#/components/schemas/DeskPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DeskPayload]"},"ApiResponse_DialerAgentsListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DialerAgentsListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DialerAgentsListResponse]"},"ApiResponse_DialerListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/DialerListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DialerListPayload]"},"ApiResponse_DialerNumbersListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DialerNumbersListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DialerNumbersListResponse]"},"ApiResponse_DialerPayload_":{"properties":{"data":{"$ref":"#/components/schemas/DialerPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DialerPayload]"},"ApiResponse_DialerSessionCreateResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DialerSessionCreateResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DialerSessionCreateResponse]"},"ApiResponse_DialerSessionResumeResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DialerSessionResumeResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DialerSessionResumeResponse]"},"ApiResponse_DialerSessionStatusUpdateResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DialerSessionStatusUpdateResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DialerSessionStatusUpdateResponse]"},"ApiResponse_DialerSessionsListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DialerSessionsListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DialerSessionsListResponse]"},"ApiResponse_DialerStatsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DialerStatsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DialerStatsResponse]"},"ApiResponse_DocumentListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/DocumentListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DocumentListPayload]"},"ApiResponse_DocumentPayload_":{"properties":{"data":{"$ref":"#/components/schemas/DocumentPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DocumentPayload]"},"ApiResponse_DomainResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DomainResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DomainResponse]"},"ApiResponse_DomainVerificationInstructions_":{"properties":{"data":{"$ref":"#/components/schemas/DomainVerificationInstructions"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DomainVerificationInstructions]"},"ApiResponse_DraftResponse_":{"properties":{"data":{"$ref":"#/components/schemas/DraftResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[DraftResponse]"},"ApiResponse_EnrichJobResponse_":{"properties":{"data":{"$ref":"#/components/schemas/EnrichJobResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[EnrichJobResponse]"},"ApiResponse_EnrichmentListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/EnrichmentListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[EnrichmentListPayload]"},"ApiResponse_EnrichmentPayload_":{"properties":{"data":{"$ref":"#/components/schemas/EnrichmentPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[EnrichmentPayload]"},"ApiResponse_EnrichmentPreflightResponse_":{"properties":{"data":{"$ref":"#/components/schemas/EnrichmentPreflightResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[EnrichmentPreflightResponse]"},"ApiResponse_EnvelopeListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/EnvelopeListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[EnvelopeListPayload]"},"ApiResponse_EnvelopePayload_":{"properties":{"data":{"$ref":"#/components/schemas/EnvelopePayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[EnvelopePayload]"},"ApiResponse_FillColumnPreviewPayload_":{"properties":{"data":{"$ref":"#/components/schemas/FillColumnPreviewPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[FillColumnPreviewPayload]"},"ApiResponse_FormOverview_":{"properties":{"data":{"$ref":"#/components/schemas/FormOverview"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[FormOverview]"},"ApiResponse_FormPayload_":{"properties":{"data":{"$ref":"#/components/schemas/FormPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[FormPayload]"},"ApiResponse_FormsAdminPayload_":{"properties":{"data":{"$ref":"#/components/schemas/FormsAdminPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[FormsAdminPayload]"},"ApiResponse_FormsListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/FormsListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[FormsListResponse]"},"ApiResponse_FormulaFunctionsPayload_":{"properties":{"data":{"$ref":"#/components/schemas/FormulaFunctionsPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[FormulaFunctionsPayload]"},"ApiResponse_FormulaValidateResponse_":{"properties":{"data":{"$ref":"#/components/schemas/FormulaValidateResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[FormulaValidateResponse]"},"ApiResponse_GenerateAppPageResponse_":{"properties":{"data":{"$ref":"#/components/schemas/GenerateAppPageResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[GenerateAppPageResponse]"},"ApiResponse_GenerateSpintaxResponse_":{"properties":{"data":{"$ref":"#/components/schemas/GenerateSpintaxResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[GenerateSpintaxResponse]"},"ApiResponse_GetFieldValueResponse_":{"properties":{"data":{"$ref":"#/components/schemas/GetFieldValueResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[GetFieldValueResponse]"},"ApiResponse_GtmLibraryListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/GtmLibraryListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[GtmLibraryListPayload]"},"ApiResponse_GtmLibraryPayload_":{"properties":{"data":{"$ref":"#/components/schemas/GtmLibraryPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[GtmLibraryPayload]"},"ApiResponse_HotContactsResult_":{"properties":{"data":{"$ref":"#/components/schemas/HotContactsResult"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[HotContactsResult]"},"ApiResponse_ImportContactsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ImportContactsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ImportContactsResponse]"},"ApiResponse_InboxListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/InboxListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[InboxListPayload]"},"ApiResponse_InboxOpsListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/InboxOpsListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[InboxOpsListPayload]"},"ApiResponse_InboxPage_":{"properties":{"data":{"$ref":"#/components/schemas/InboxPage"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[InboxPage]"},"ApiResponse_InboxPayload_":{"properties":{"data":{"$ref":"#/components/schemas/InboxPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[InboxPayload]"},"ApiResponse_InboxThreadResponse_":{"properties":{"data":{"$ref":"#/components/schemas/InboxThreadResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[InboxThreadResponse]"},"ApiResponse_InstalledAppResponse_":{"properties":{"data":{"$ref":"#/components/schemas/InstalledAppResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[InstalledAppResponse]"},"ApiResponse_IntegrationOpPayload_":{"properties":{"data":{"$ref":"#/components/schemas/IntegrationOpPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[IntegrationOpPayload]"},"ApiResponse_IntegrationStatusPayload_":{"properties":{"data":{"$ref":"#/components/schemas/IntegrationStatusPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[IntegrationStatusPayload]"},"ApiResponse_IntelligenceListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/IntelligenceListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[IntelligenceListPayload]"},"ApiResponse_IntelligencePayload_":{"properties":{"data":{"$ref":"#/components/schemas/IntelligencePayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[IntelligencePayload]"},"ApiResponse_IntentPayload_":{"properties":{"data":{"$ref":"#/components/schemas/IntentPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[IntentPayload]"},"ApiResponse_IntentSignalsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/IntentSignalsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[IntentSignalsResponse]"},"ApiResponse_InvokeActionResponse_":{"properties":{"data":{"$ref":"#/components/schemas/InvokeActionResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[InvokeActionResponse]"},"ApiResponse_IssueAnalyticsKpis_":{"properties":{"data":{"$ref":"#/components/schemas/IssueAnalyticsKpis"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[IssueAnalyticsKpis]"},"ApiResponse_IssueDetail_":{"properties":{"data":{"$ref":"#/components/schemas/IssueDetail"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[IssueDetail]"},"ApiResponse_JobChangeSignalsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/JobChangeSignalsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[JobChangeSignalsResponse]"},"ApiResponse_JobDetails_":{"properties":{"data":{"$ref":"#/components/schemas/JobDetails"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[JobDetails]"},"ApiResponse_JobSearchResponse_":{"properties":{"data":{"$ref":"#/components/schemas/JobSearchResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[JobSearchResponse]"},"ApiResponse_KeywordCreateFromDomainResponse_":{"properties":{"data":{"$ref":"#/components/schemas/KeywordCreateFromDomainResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[KeywordCreateFromDomainResponse]"},"ApiResponse_KeywordsAddResponse_":{"properties":{"data":{"$ref":"#/components/schemas/KeywordsAddResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[KeywordsAddResponse]"},"ApiResponse_KeywordsCreateFromSearchResponse_":{"properties":{"data":{"$ref":"#/components/schemas/KeywordsCreateFromSearchResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[KeywordsCreateFromSearchResponse]"},"ApiResponse_LeadContentPayload_":{"properties":{"data":{"$ref":"#/components/schemas/LeadContentPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[LeadContentPayload]"},"ApiResponse_LeadPreviewResponse_":{"properties":{"data":{"$ref":"#/components/schemas/LeadPreviewResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[LeadPreviewResponse]"},"ApiResponse_LeadStatusesResponse_":{"properties":{"data":{"$ref":"#/components/schemas/LeadStatusesResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[LeadStatusesResponse]"},"ApiResponse_LifecycleLeadStatusesPayload_":{"properties":{"data":{"$ref":"#/components/schemas/LifecycleLeadStatusesPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[LifecycleLeadStatusesPayload]"},"ApiResponse_LifecycleStageMoveResponse_":{"properties":{"data":{"$ref":"#/components/schemas/LifecycleStageMoveResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[LifecycleStageMoveResponse]"},"ApiResponse_LinkedInAccountPlans_":{"properties":{"data":{"$ref":"#/components/schemas/LinkedInAccountPlans"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[LinkedInAccountPlans]"},"ApiResponse_LinkedInAccountSyncResult_":{"properties":{"data":{"$ref":"#/components/schemas/LinkedInAccountSyncResult"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[LinkedInAccountSyncResult]"},"ApiResponse_LinkedInApprovalPayload_":{"properties":{"data":{"$ref":"#/components/schemas/LinkedInApprovalPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[LinkedInApprovalPayload]"},"ApiResponse_LinkedInChannelRemovalResponse_":{"properties":{"data":{"$ref":"#/components/schemas/LinkedInChannelRemovalResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[LinkedInChannelRemovalResponse]"},"ApiResponse_LinkedInConnectionStatus_":{"properties":{"data":{"$ref":"#/components/schemas/LinkedInConnectionStatus"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[LinkedInConnectionStatus]"},"ApiResponse_LinkedInScheduleState_":{"properties":{"data":{"$ref":"#/components/schemas/LinkedInScheduleState"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[LinkedInScheduleState]"},"ApiResponse_LinkedInSchedule_":{"properties":{"data":{"$ref":"#/components/schemas/LinkedInSchedule"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[LinkedInSchedule]"},"ApiResponse_ListCollectionPayload_":{"properties":{"data":{"$ref":"#/components/schemas/ListCollectionPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ListCollectionPayload]"},"ApiResponse_ListCreateResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ListCreateResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ListCreateResponse]"},"ApiResponse_ListDownloadPayload_":{"properties":{"data":{"$ref":"#/components/schemas/ListDownloadPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ListDownloadPayload]"},"ApiResponse_ListFolderIndexResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ListFolderIndexResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ListFolderIndexResponse]"},"ApiResponse_ListFolderResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ListFolderResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ListFolderResponse]"},"ApiResponse_ListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/ListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ListPayload]"},"ApiResponse_ListPerformanceResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ListPerformanceResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ListPerformanceResponse]"},"ApiResponse_ListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ListResponse]"},"ApiResponse_ListSyncListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ListSyncListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ListSyncListResponse]"},"ApiResponse_List_ProviderDomainResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/ProviderDomainResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[List[ProviderDomainResponse]]"},"ApiResponse_List_SeoAudit__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SeoAudit"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[List[SeoAudit]]"},"ApiResponse_List_SeoTrackedKeyword__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SeoTrackedKeyword"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[List[SeoTrackedKeyword]]"},"ApiResponse_LookupResponse_":{"properties":{"data":{"$ref":"#/components/schemas/LookupResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[LookupResponse]"},"ApiResponse_MailboxAssociatedSequencesResponse_":{"properties":{"data":{"$ref":"#/components/schemas/MailboxAssociatedSequencesResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MailboxAssociatedSequencesResponse]"},"ApiResponse_MailboxDeleteResponse_":{"properties":{"data":{"$ref":"#/components/schemas/MailboxDeleteResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MailboxDeleteResponse]"},"ApiResponse_MailboxDomainListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/MailboxDomainListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MailboxDomainListPayload]"},"ApiResponse_MailboxDomainPayload_":{"properties":{"data":{"$ref":"#/components/schemas/MailboxDomainPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MailboxDomainPayload]"},"ApiResponse_MailboxFleetHealthResponse_":{"properties":{"data":{"$ref":"#/components/schemas/MailboxFleetHealthResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MailboxFleetHealthResponse]"},"ApiResponse_MailboxHealthResponse_":{"properties":{"data":{"$ref":"#/components/schemas/MailboxHealthResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MailboxHealthResponse]"},"ApiResponse_MailboxOverviewPayload_":{"properties":{"data":{"$ref":"#/components/schemas/MailboxOverviewPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MailboxOverviewPayload]"},"ApiResponse_MailboxRecoveryListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/MailboxRecoveryListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MailboxRecoveryListPayload]"},"ApiResponse_MailboxRecoveryPayload_":{"properties":{"data":{"$ref":"#/components/schemas/MailboxRecoveryPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MailboxRecoveryPayload]"},"ApiResponse_MailboxResponse_":{"properties":{"data":{"$ref":"#/components/schemas/MailboxResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MailboxResponse]"},"ApiResponse_MarketplaceConnectStatusResponse_":{"properties":{"data":{"$ref":"#/components/schemas/MarketplaceConnectStatusResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MarketplaceConnectStatusResponse]"},"ApiResponse_MarketplaceHiringsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/MarketplaceHiringsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MarketplaceHiringsResponse]"},"ApiResponse_MarketplaceInvoicesResponse_":{"properties":{"data":{"$ref":"#/components/schemas/MarketplaceInvoicesResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MarketplaceInvoicesResponse]"},"ApiResponse_MarketplaceListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/MarketplaceListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MarketplaceListPayload]"},"ApiResponse_MarketplaceMeetingDetail_":{"properties":{"data":{"$ref":"#/components/schemas/MarketplaceMeetingDetail"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MarketplaceMeetingDetail]"},"ApiResponse_MarketplaceMeetingsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/MarketplaceMeetingsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MarketplaceMeetingsResponse]"},"ApiResponse_MarketplaceOffersResponse_":{"properties":{"data":{"$ref":"#/components/schemas/MarketplaceOffersResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MarketplaceOffersResponse]"},"ApiResponse_MarketplacePayload_":{"properties":{"data":{"$ref":"#/components/schemas/MarketplacePayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MarketplacePayload]"},"ApiResponse_MarketplacePayoutAccountResponse_":{"properties":{"data":{"$ref":"#/components/schemas/MarketplacePayoutAccountResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MarketplacePayoutAccountResponse]"},"ApiResponse_MarketplaceProfileResponse_":{"properties":{"data":{"$ref":"#/components/schemas/MarketplaceProfileResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MarketplaceProfileResponse]"},"ApiResponse_McpConnectionStatus_":{"properties":{"data":{"$ref":"#/components/schemas/McpConnectionStatus"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[McpConnectionStatus]"},"ApiResponse_MeetingDetail_":{"properties":{"data":{"$ref":"#/components/schemas/MeetingDetail"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MeetingDetail]"},"ApiResponse_MeetingsBookedResult_":{"properties":{"data":{"$ref":"#/components/schemas/MeetingsBookedResult"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MeetingsBookedResult]"},"ApiResponse_MissedCallbacksResponse_":{"properties":{"data":{"$ref":"#/components/schemas/MissedCallbacksResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MissedCallbacksResponse]"},"ApiResponse_MyMailboxesResponse_":{"properties":{"data":{"$ref":"#/components/schemas/MyMailboxesResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[MyMailboxesResponse]"},"ApiResponse_NewsletterDetail_":{"properties":{"data":{"$ref":"#/components/schemas/NewsletterDetail"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[NewsletterDetail]"},"ApiResponse_NewsletterListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/NewsletterListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[NewsletterListPayload]"},"ApiResponse_NewsletterPayload_":{"properties":{"data":{"$ref":"#/components/schemas/NewsletterPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[NewsletterPayload]"},"ApiResponse_NewsletterStatusResponse_":{"properties":{"data":{"$ref":"#/components/schemas/NewsletterStatusResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[NewsletterStatusResponse]"},"ApiResponse_NewsletterStudioPayload_":{"properties":{"data":{"$ref":"#/components/schemas/NewsletterStudioPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[NewsletterStudioPayload]"},"ApiResponse_NoneType_":{"properties":{"data":{"type":"null","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[NoneType]"},"ApiResponse_NoteResponse_":{"properties":{"data":{"$ref":"#/components/schemas/NoteResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[NoteResponse]"},"ApiResponse_NurtureListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/NurtureListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[NurtureListResponse]"},"ApiResponse_NurtureResponse_":{"properties":{"data":{"$ref":"#/components/schemas/NurtureResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[NurtureResponse]"},"ApiResponse_ObjectCsvInspection_":{"properties":{"data":{"$ref":"#/components/schemas/ObjectCsvInspection"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ObjectCsvInspection]"},"ApiResponse_ObjectCsvPreview_":{"properties":{"data":{"$ref":"#/components/schemas/ObjectCsvPreview"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ObjectCsvPreview]"},"ApiResponse_ObjectCsvReceipt_":{"properties":{"data":{"$ref":"#/components/schemas/ObjectCsvReceipt"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ObjectCsvReceipt]"},"ApiResponse_ObjectDefinitionResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ObjectDefinitionResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ObjectDefinitionResponse]"},"ApiResponse_ObjectImportDetail_":{"properties":{"data":{"$ref":"#/components/schemas/ObjectImportDetail"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ObjectImportDetail]"},"ApiResponse_ObjectRecordResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ObjectRecordResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ObjectRecordResponse]"},"ApiResponse_OnboardingPayload_":{"properties":{"data":{"$ref":"#/components/schemas/OnboardingPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OnboardingPayload]"},"ApiResponse_OpenSearchAggregateResponse_":{"properties":{"data":{"$ref":"#/components/schemas/OpenSearchAggregateResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OpenSearchAggregateResponse]"},"ApiResponse_OpenSearchCountResponse_":{"properties":{"data":{"$ref":"#/components/schemas/OpenSearchCountResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OpenSearchCountResponse]"},"ApiResponse_OpenSearchResolveResponse_":{"properties":{"data":{"$ref":"#/components/schemas/OpenSearchResolveResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OpenSearchResolveResponse]"},"ApiResponse_OpenSearchSearchResponse_":{"properties":{"data":{"$ref":"#/components/schemas/OpenSearchSearchResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OpenSearchSearchResponse]"},"ApiResponse_OperatorListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/OperatorListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OperatorListPayload]"},"ApiResponse_OperatorPayload_":{"properties":{"data":{"$ref":"#/components/schemas/OperatorPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OperatorPayload]"},"ApiResponse_OpsSequenceBindingsReport_":{"properties":{"data":{"$ref":"#/components/schemas/OpsSequenceBindingsReport"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OpsSequenceBindingsReport]"},"ApiResponse_OrgEventFeedPage_":{"properties":{"data":{"$ref":"#/components/schemas/OrgEventFeedPage"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OrgEventFeedPage]"},"ApiResponse_OrgGovernancePayload_":{"properties":{"data":{"$ref":"#/components/schemas/OrgGovernancePayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OrgGovernancePayload]"},"ApiResponse_OrgListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/OrgListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OrgListPayload]"},"ApiResponse_OrgPayload_":{"properties":{"data":{"$ref":"#/components/schemas/OrgPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OrgPayload]"},"ApiResponse_OrgSummaryDTO_":{"properties":{"data":{"$ref":"#/components/schemas/OrgSummaryDTO"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OrgSummaryDTO]"},"ApiResponse_OrgVideoListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/OrgVideoListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OrgVideoListPayload]"},"ApiResponse_OrgVideoPayload_":{"properties":{"data":{"$ref":"#/components/schemas/OrgVideoPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OrgVideoPayload]"},"ApiResponse_OutreachCampaignActionResult_":{"properties":{"data":{"$ref":"#/components/schemas/OutreachCampaignActionResult"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OutreachCampaignActionResult]"},"ApiResponse_OutreachCampaignLeads_":{"properties":{"data":{"$ref":"#/components/schemas/OutreachCampaignLeads"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OutreachCampaignLeads]"},"ApiResponse_OutreachCampaignProgress_":{"properties":{"data":{"$ref":"#/components/schemas/OutreachCampaignProgress"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OutreachCampaignProgress]"},"ApiResponse_OutreachCampaignStats_":{"properties":{"data":{"$ref":"#/components/schemas/OutreachCampaignStats"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OutreachCampaignStats]"},"ApiResponse_OutreachCampaigns_":{"properties":{"data":{"$ref":"#/components/schemas/OutreachCampaigns"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OutreachCampaigns]"},"ApiResponse_OutreachConnectionStatus_":{"properties":{"data":{"$ref":"#/components/schemas/OutreachConnectionStatus"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OutreachConnectionStatus]"},"ApiResponse_OutreachLeadsAdded_":{"properties":{"data":{"$ref":"#/components/schemas/OutreachLeadsAdded"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OutreachLeadsAdded]"},"ApiResponse_OutreachListCreated_":{"properties":{"data":{"$ref":"#/components/schemas/OutreachListCreated"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OutreachListCreated]"},"ApiResponse_OutreachLists_":{"properties":{"data":{"$ref":"#/components/schemas/OutreachLists"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OutreachLists]"},"ApiResponse_OutreachReconnectResult_":{"properties":{"data":{"$ref":"#/components/schemas/OutreachReconnectResult"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OutreachReconnectResult]"},"ApiResponse_OutreachSenderAccounts_":{"properties":{"data":{"$ref":"#/components/schemas/OutreachSenderAccounts"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OutreachSenderAccounts]"},"ApiResponse_OutreachSequenceMapping_":{"properties":{"data":{"$ref":"#/components/schemas/OutreachSequenceMapping"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OutreachSequenceMapping]"},"ApiResponse_OutreachStepCampaigns_":{"properties":{"data":{"$ref":"#/components/schemas/OutreachStepCampaigns"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OutreachStepCampaigns]"},"ApiResponse_OutreachTemplates_":{"properties":{"data":{"$ref":"#/components/schemas/OutreachTemplates"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OutreachTemplates]"},"ApiResponse_OutreachWorkspaceSelected_":{"properties":{"data":{"$ref":"#/components/schemas/OutreachWorkspaceSelected"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OutreachWorkspaceSelected]"},"ApiResponse_OutreachWorkspaceState_":{"properties":{"data":{"$ref":"#/components/schemas/OutreachWorkspaceState"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OutreachWorkspaceState]"},"ApiResponse_OutreachWorkspaces_":{"properties":{"data":{"$ref":"#/components/schemas/OutreachWorkspaces"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[OutreachWorkspaces]"},"ApiResponse_PagesByDomainResponse_":{"properties":{"data":{"$ref":"#/components/schemas/PagesByDomainResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[PagesByDomainResponse]"},"ApiResponse_PagesSearchResponse_":{"properties":{"data":{"$ref":"#/components/schemas/PagesSearchResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[PagesSearchResponse]"},"ApiResponse_PatchSetResponse_":{"properties":{"data":{"$ref":"#/components/schemas/PatchSetResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[PatchSetResponse]"},"ApiResponse_PhoneA2pStatusPayload_":{"properties":{"data":{"$ref":"#/components/schemas/PhoneA2pStatusPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[PhoneA2pStatusPayload]"},"ApiResponse_PhoneNumberPayload_":{"properties":{"data":{"$ref":"#/components/schemas/PhoneNumberPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[PhoneNumberPayload]"},"ApiResponse_PhoneNumberSearchPayload_":{"properties":{"data":{"$ref":"#/components/schemas/PhoneNumberSearchPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[PhoneNumberSearchPayload]"},"ApiResponse_PipelineByChannelPayload_":{"properties":{"data":{"$ref":"#/components/schemas/PipelineByChannelPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[PipelineByChannelPayload]"},"ApiResponse_PipelineBySourceDealsPayload_":{"properties":{"data":{"$ref":"#/components/schemas/PipelineBySourceDealsPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[PipelineBySourceDealsPayload]"},"ApiResponse_PipelineBySourcePayload_":{"properties":{"data":{"$ref":"#/components/schemas/PipelineBySourcePayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[PipelineBySourcePayload]"},"ApiResponse_PipelineResponse_":{"properties":{"data":{"$ref":"#/components/schemas/PipelineResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[PipelineResponse]"},"ApiResponse_PipelineStageResponse_":{"properties":{"data":{"$ref":"#/components/schemas/PipelineStageResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[PipelineStageResponse]"},"ApiResponse_ProcessListEntryResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ProcessListEntryResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ProcessListEntryResponse]"},"ApiResponse_ProcessListListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ProcessListListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ProcessListListResponse]"},"ApiResponse_ProcessListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ProcessListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ProcessListResponse]"},"ApiResponse_ProviderCatalogResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ProviderCatalogResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ProviderCatalogResponse]"},"ApiResponse_ProviderUsagePayload_":{"properties":{"data":{"$ref":"#/components/schemas/ProviderUsagePayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ProviderUsagePayload]"},"ApiResponse_PublicCopilotResponse_":{"properties":{"data":{"$ref":"#/components/schemas/PublicCopilotResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[PublicCopilotResponse]"},"ApiResponse_PublicEnrichResponse_":{"properties":{"data":{"$ref":"#/components/schemas/PublicEnrichResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[PublicEnrichResponse]"},"ApiResponse_PublishSchemaVersionResponse_":{"properties":{"data":{"$ref":"#/components/schemas/PublishSchemaVersionResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[PublishSchemaVersionResponse]"},"ApiResponse_QuotableProductsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/QuotableProductsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[QuotableProductsResponse]"},"ApiResponse_QuoteDetail_":{"properties":{"data":{"$ref":"#/components/schemas/QuoteDetail"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[QuoteDetail]"},"ApiResponse_QuoteListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/QuoteListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[QuoteListPayload]"},"ApiResponse_QuoteListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/QuoteListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[QuoteListResponse]"},"ApiResponse_QuotePayload_":{"properties":{"data":{"$ref":"#/components/schemas/QuotePayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[QuotePayload]"},"ApiResponse_QuoteSettingsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/QuoteSettingsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[QuoteSettingsResponse]"},"ApiResponse_RadarReportListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/RadarReportListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RadarReportListPayload]"},"ApiResponse_RadarReportPayload_":{"properties":{"data":{"$ref":"#/components/schemas/RadarReportPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RadarReportPayload]"},"ApiResponse_RecalculateResponse_":{"properties":{"data":{"$ref":"#/components/schemas/RecalculateResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RecalculateResponse]"},"ApiResponse_RecordBulkArchiveResponse_":{"properties":{"data":{"$ref":"#/components/schemas/RecordBulkArchiveResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RecordBulkArchiveResponse]"},"ApiResponse_RecordBulkUpdateResponse_":{"properties":{"data":{"$ref":"#/components/schemas/RecordBulkUpdateResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RecordBulkUpdateResponse]"},"ApiResponse_RecordHistoryResponse_":{"properties":{"data":{"$ref":"#/components/schemas/RecordHistoryResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RecordHistoryResponse]"},"ApiResponse_RecordListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/RecordListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RecordListResponse]"},"ApiResponse_RecordMergeResponse_":{"properties":{"data":{"$ref":"#/components/schemas/RecordMergeResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RecordMergeResponse]"},"ApiResponse_RecordMutationsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/RecordMutationsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RecordMutationsResponse]"},"ApiResponse_RecordRelationshipsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/RecordRelationshipsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RecordRelationshipsResponse]"},"ApiResponse_RecordRolePayload_":{"properties":{"data":{"$ref":"#/components/schemas/RecordRolePayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RecordRolePayload]"},"ApiResponse_RelationshipDefinitionListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/RelationshipDefinitionListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RelationshipDefinitionListResponse]"},"ApiResponse_RelationshipDefinitionResponse_":{"properties":{"data":{"$ref":"#/components/schemas/RelationshipDefinitionResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RelationshipDefinitionResponse]"},"ApiResponse_RelationshipGridCellsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/RelationshipGridCellsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RelationshipGridCellsResponse]"},"ApiResponse_RelationshipResponse_":{"properties":{"data":{"$ref":"#/components/schemas/RelationshipResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RelationshipResponse]"},"ApiResponse_RelationshipTargetsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/RelationshipTargetsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RelationshipTargetsResponse]"},"ApiResponse_RepoResponse_":{"properties":{"data":{"$ref":"#/components/schemas/RepoResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RepoResponse]"},"ApiResponse_ReportDefinitionResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ReportDefinitionResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ReportDefinitionResponse]"},"ApiResponse_ReportListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/ReportListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ReportListPayload]"},"ApiResponse_ReportListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ReportListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ReportListResponse]"},"ApiResponse_ReportNativeFieldsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ReportNativeFieldsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ReportNativeFieldsResponse]"},"ApiResponse_ReportPayload_":{"properties":{"data":{"$ref":"#/components/schemas/ReportPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ReportPayload]"},"ApiResponse_ReportResult_":{"properties":{"data":{"$ref":"#/components/schemas/ReportResult"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ReportResult]"},"ApiResponse_RestoreJobListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/RestoreJobListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RestoreJobListResponse]"},"ApiResponse_RestoreJobResponse_":{"properties":{"data":{"$ref":"#/components/schemas/RestoreJobResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RestoreJobResponse]"},"ApiResponse_RevenueAnalyticsPayload_":{"properties":{"data":{"$ref":"#/components/schemas/RevenueAnalyticsPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RevenueAnalyticsPayload]"},"ApiResponse_RevenueRecordListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/RevenueRecordListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RevenueRecordListPayload]"},"ApiResponse_RevenueRecordPayload_":{"properties":{"data":{"$ref":"#/components/schemas/RevenueRecordPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[RevenueRecordPayload]"},"ApiResponse_SavedViewResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SavedViewResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SavedViewResponse]"},"ApiResponse_ScanResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ScanResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ScanResponse]"},"ApiResponse_SchedulingListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/SchedulingListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SchedulingListPayload]"},"ApiResponse_SchedulingPayload_":{"properties":{"data":{"$ref":"#/components/schemas/SchedulingPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SchedulingPayload]"},"ApiResponse_ScopeCatalogResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ScopeCatalogResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ScopeCatalogResponse]"},"ApiResponse_SearchCountVariantsPayload_":{"properties":{"data":{"$ref":"#/components/schemas/SearchCountVariantsPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SearchCountVariantsPayload]"},"ApiResponse_SearchDiscoveryPayload_":{"properties":{"data":{"$ref":"#/components/schemas/SearchDiscoveryPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SearchDiscoveryPayload]"},"ApiResponse_SearchSaveResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SearchSaveResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SearchSaveResponse]"},"ApiResponse_SendResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SendResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SendResponse]"},"ApiResponse_SeoAgentFixPack_":{"properties":{"data":{"$ref":"#/components/schemas/SeoAgentFixPack"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoAgentFixPack]"},"ApiResponse_SeoAgentFixQueue_":{"properties":{"data":{"$ref":"#/components/schemas/SeoAgentFixQueue"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoAgentFixQueue]"},"ApiResponse_SeoAgentHandoff_":{"properties":{"data":{"$ref":"#/components/schemas/SeoAgentHandoff"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoAgentHandoff]"},"ApiResponse_SeoAiReadiness_":{"properties":{"data":{"$ref":"#/components/schemas/SeoAiReadiness"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoAiReadiness]"},"ApiResponse_SeoAuditIssues_":{"properties":{"data":{"$ref":"#/components/schemas/SeoAuditIssues"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoAuditIssues]"},"ApiResponse_SeoAudit_":{"properties":{"data":{"$ref":"#/components/schemas/SeoAudit"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoAudit]"},"ApiResponse_SeoBacklinksOverview_":{"properties":{"data":{"$ref":"#/components/schemas/SeoBacklinksOverview"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoBacklinksOverview]"},"ApiResponse_SeoCheckKeywordsNowResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SeoCheckKeywordsNowResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoCheckKeywordsNowResponse]"},"ApiResponse_SeoClaimFixResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SeoClaimFixResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoClaimFixResponse]"},"ApiResponse_SeoCompleteFixResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SeoCompleteFixResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoCompleteFixResponse]"},"ApiResponse_SeoDomainOverviewResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SeoDomainOverviewResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoDomainOverviewResponse]"},"ApiResponse_SeoDomainPages_":{"properties":{"data":{"$ref":"#/components/schemas/SeoDomainPages"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoDomainPages]"},"ApiResponse_SeoPage360_":{"properties":{"data":{"$ref":"#/components/schemas/SeoPage360"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoPage360]"},"ApiResponse_SeoPages360_":{"properties":{"data":{"$ref":"#/components/schemas/SeoPages360"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoPages360]"},"ApiResponse_SeoRankHistory_":{"properties":{"data":{"$ref":"#/components/schemas/SeoRankHistory"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoRankHistory]"},"ApiResponse_SeoRemovedDomain_":{"properties":{"data":{"$ref":"#/components/schemas/SeoRemovedDomain"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoRemovedDomain]"},"ApiResponse_SeoRemovedKeywords_":{"properties":{"data":{"$ref":"#/components/schemas/SeoRemovedKeywords"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoRemovedKeywords]"},"ApiResponse_SeoResearchKeywordsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SeoResearchKeywordsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoResearchKeywordsResponse]"},"ApiResponse_SeoShareOfVoice_":{"properties":{"data":{"$ref":"#/components/schemas/SeoShareOfVoice"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoShareOfVoice]"},"ApiResponse_SeoToday_":{"properties":{"data":{"$ref":"#/components/schemas/SeoToday"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoToday]"},"ApiResponse_SeoTrackedDomainDetail_":{"properties":{"data":{"$ref":"#/components/schemas/SeoTrackedDomainDetail"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoTrackedDomainDetail]"},"ApiResponse_SeoTrackedDomains_":{"properties":{"data":{"$ref":"#/components/schemas/SeoTrackedDomains"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoTrackedDomains]"},"ApiResponse_SeoUpdatedKeywords_":{"properties":{"data":{"$ref":"#/components/schemas/SeoUpdatedKeywords"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SeoUpdatedKeywords]"},"ApiResponse_SequenceActionResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SequenceActionResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SequenceActionResponse]"},"ApiResponse_SequenceAnalyticsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SequenceAnalyticsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SequenceAnalyticsResponse]"},"ApiResponse_SequenceCalendarPayload_":{"properties":{"data":{"$ref":"#/components/schemas/SequenceCalendarPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SequenceCalendarPayload]"},"ApiResponse_SequenceCreateResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SequenceCreateResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SequenceCreateResponse]"},"ApiResponse_SequenceDetailResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SequenceDetailResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SequenceDetailResponse]"},"ApiResponse_SequenceInmailPayload_":{"properties":{"data":{"$ref":"#/components/schemas/SequenceInmailPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SequenceInmailPayload]"},"ApiResponse_SequenceMixAndMatchPayload_":{"properties":{"data":{"$ref":"#/components/schemas/SequenceMixAndMatchPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SequenceMixAndMatchPayload]"},"ApiResponse_SequenceOpsPayload_":{"properties":{"data":{"$ref":"#/components/schemas/SequenceOpsPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SequenceOpsPayload]"},"ApiResponse_SequencePreviewResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SequencePreviewResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SequencePreviewResponse]"},"ApiResponse_SequenceRecord_":{"properties":{"data":{"$ref":"#/components/schemas/SequenceRecord"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SequenceRecord]"},"ApiResponse_SequenceRelatedRecordsPayload_":{"properties":{"data":{"$ref":"#/components/schemas/SequenceRelatedRecordsPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SequenceRelatedRecordsPayload]"},"ApiResponse_SequenceRoutingSummary_":{"properties":{"data":{"$ref":"#/components/schemas/SequenceRoutingSummary"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SequenceRoutingSummary]"},"ApiResponse_SequenceStats_":{"properties":{"data":{"$ref":"#/components/schemas/SequenceStats"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SequenceStats]"},"ApiResponse_SequenceStepsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SequenceStepsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SequenceStepsResponse]"},"ApiResponse_SequencerListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/SequencerListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SequencerListPayload]"},"ApiResponse_SequencerPayload_":{"properties":{"data":{"$ref":"#/components/schemas/SequencerPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SequencerPayload]"},"ApiResponse_SetFieldValueResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SetFieldValueResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SetFieldValueResponse]"},"ApiResponse_SetFieldValuesBatchResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SetFieldValuesBatchResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SetFieldValuesBatchResponse]"},"ApiResponse_SettingsListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/SettingsListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SettingsListPayload]"},"ApiResponse_SettingsPayload_":{"properties":{"data":{"$ref":"#/components/schemas/SettingsPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SettingsPayload]"},"ApiResponse_SignatureArchiveResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SignatureArchiveResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SignatureArchiveResponse]"},"ApiResponse_SignatureBulkTemplateResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SignatureBulkTemplateResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SignatureBulkTemplateResponse]"},"ApiResponse_SignatureCampaignPreviewResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SignatureCampaignPreviewResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SignatureCampaignPreviewResponse]"},"ApiResponse_SignatureCampaignResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SignatureCampaignResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SignatureCampaignResponse]"},"ApiResponse_SignatureDeploymentStatus_":{"properties":{"data":{"$ref":"#/components/schemas/SignatureDeploymentStatus"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SignatureDeploymentStatus]"},"ApiResponse_SignatureSettingsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SignatureSettingsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SignatureSettingsResponse]"},"ApiResponse_SignatureTemplateResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SignatureTemplateResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SignatureTemplateResponse]"},"ApiResponse_SignatureVersionResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SignatureVersionResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SignatureVersionResponse]"},"ApiResponse_SiteConnectionsPayload_":{"properties":{"data":{"$ref":"#/components/schemas/SiteConnectionsPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SiteConnectionsPayload]"},"ApiResponse_SnippetResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SnippetResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SnippetResponse]"},"ApiResponse_SocialAccountList_":{"properties":{"data":{"$ref":"#/components/schemas/SocialAccountList"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SocialAccountList]"},"ApiResponse_SocialAnalytics_":{"properties":{"data":{"$ref":"#/components/schemas/SocialAnalytics"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SocialAnalytics]"},"ApiResponse_SocialAudienceFromEngagers_":{"properties":{"data":{"$ref":"#/components/schemas/SocialAudienceFromEngagers"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SocialAudienceFromEngagers]"},"ApiResponse_SocialAutopilot_":{"properties":{"data":{"$ref":"#/components/schemas/SocialAutopilot"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SocialAutopilot]"},"ApiResponse_SocialCollection_":{"properties":{"data":{"$ref":"#/components/schemas/SocialCollection"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SocialCollection]"},"ApiResponse_SocialDeleted_":{"properties":{"data":{"$ref":"#/components/schemas/SocialDeleted"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SocialDeleted]"},"ApiResponse_SocialEngagers_":{"properties":{"data":{"$ref":"#/components/schemas/SocialEngagers"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SocialEngagers]"},"ApiResponse_SocialEnrollResult_":{"properties":{"data":{"$ref":"#/components/schemas/SocialEnrollResult"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SocialEnrollResult]"},"ApiResponse_SocialGenerated_":{"properties":{"data":{"$ref":"#/components/schemas/SocialGenerated"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SocialGenerated]"},"ApiResponse_SocialGenerationContext_":{"properties":{"data":{"$ref":"#/components/schemas/SocialGenerationContext"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SocialGenerationContext]"},"ApiResponse_SocialIdeas_":{"properties":{"data":{"$ref":"#/components/schemas/SocialIdeas"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SocialIdeas]"},"ApiResponse_SocialPayload_":{"properties":{"data":{"$ref":"#/components/schemas/SocialPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SocialPayload]"},"ApiResponse_SocialPostMetrics_":{"properties":{"data":{"$ref":"#/components/schemas/SocialPostMetrics"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SocialPostMetrics]"},"ApiResponse_SocialPostPage_":{"properties":{"data":{"$ref":"#/components/schemas/SocialPostPage"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SocialPostPage]"},"ApiResponse_SocialPost_":{"properties":{"data":{"$ref":"#/components/schemas/SocialPost"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SocialPost]"},"ApiResponse_SocialProviderList_":{"properties":{"data":{"$ref":"#/components/schemas/SocialProviderList"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SocialProviderList]"},"ApiResponse_SocialPublishAccepted_":{"properties":{"data":{"$ref":"#/components/schemas/SocialPublishAccepted"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SocialPublishAccepted]"},"ApiResponse_StagegateBacktestPayload_":{"properties":{"data":{"$ref":"#/components/schemas/StagegateBacktestPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[StagegateBacktestPayload]"},"ApiResponse_StagegateDealPanelPayload_":{"properties":{"data":{"$ref":"#/components/schemas/StagegateDealPanelPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[StagegateDealPanelPayload]"},"ApiResponse_StagegateFeedbackPayload_":{"properties":{"data":{"$ref":"#/components/schemas/StagegateFeedbackPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[StagegateFeedbackPayload]"},"ApiResponse_StagegatePacksPayload_":{"properties":{"data":{"$ref":"#/components/schemas/StagegatePacksPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[StagegatePacksPayload]"},"ApiResponse_StagegateRulesPayload_":{"properties":{"data":{"$ref":"#/components/schemas/StagegateRulesPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[StagegateRulesPayload]"},"ApiResponse_StagegateSettingsPayload_":{"properties":{"data":{"$ref":"#/components/schemas/StagegateSettingsPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[StagegateSettingsPayload]"},"ApiResponse_StagegateViewPayload_":{"properties":{"data":{"$ref":"#/components/schemas/StagegateViewPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[StagegateViewPayload]"},"ApiResponse_StudioContentListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/StudioContentListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[StudioContentListPayload]"},"ApiResponse_StudioContentPayload_":{"properties":{"data":{"$ref":"#/components/schemas/StudioContentPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[StudioContentPayload]"},"ApiResponse_StudioListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/StudioListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[StudioListPayload]"},"ApiResponse_StudioPayload_":{"properties":{"data":{"$ref":"#/components/schemas/StudioPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[StudioPayload]"},"ApiResponse_SubscriberListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SubscriberListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SubscriberListResponse]"},"ApiResponse_SubscriberSummary_":{"properties":{"data":{"$ref":"#/components/schemas/SubscriberSummary"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SubscriberSummary]"},"ApiResponse_SummaryDTO_":{"properties":{"data":{"$ref":"#/components/schemas/SummaryDTO"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SummaryDTO]"},"ApiResponse_SuppressActionResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SuppressActionResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SuppressActionResponse]"},"ApiResponse_SuppressionStatusResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SuppressionStatusResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SuppressionStatusResponse]"},"ApiResponse_SurveyDeleteResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SurveyDeleteResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SurveyDeleteResponse]"},"ApiResponse_SurveyDomainPayload_":{"properties":{"data":{"$ref":"#/components/schemas/SurveyDomainPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SurveyDomainPayload]"},"ApiResponse_SurveyResponseDTO_":{"properties":{"data":{"$ref":"#/components/schemas/SurveyResponseDTO"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SurveyResponseDTO]"},"ApiResponse_SurveyResponsesDTO_":{"properties":{"data":{"$ref":"#/components/schemas/SurveyResponsesDTO"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SurveyResponsesDTO]"},"ApiResponse_SurveySendAccepted_":{"properties":{"data":{"$ref":"#/components/schemas/SurveySendAccepted"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SurveySendAccepted]"},"ApiResponse_SurveySendDTO_":{"properties":{"data":{"$ref":"#/components/schemas/SurveySendDTO"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SurveySendDTO]"},"ApiResponse_SurveySendsDTO_":{"properties":{"data":{"$ref":"#/components/schemas/SurveySendsDTO"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SurveySendsDTO]"},"ApiResponse_SurveyTriggerDTO_":{"properties":{"data":{"$ref":"#/components/schemas/SurveyTriggerDTO"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SurveyTriggerDTO]"},"ApiResponse_SurveyTriggerDeleteResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SurveyTriggerDeleteResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SurveyTriggerDeleteResponse]"},"ApiResponse_SyncJobResponse_":{"properties":{"data":{"$ref":"#/components/schemas/SyncJobResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[SyncJobResponse]"},"ApiResponse_TaskAssignmentResult_":{"properties":{"data":{"$ref":"#/components/schemas/TaskAssignmentResult"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[TaskAssignmentResult]"},"ApiResponse_TaskExecutionHistory_":{"properties":{"data":{"$ref":"#/components/schemas/TaskExecutionHistory"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[TaskExecutionHistory]"},"ApiResponse_TaskResponse_":{"properties":{"data":{"$ref":"#/components/schemas/TaskResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[TaskResponse]"},"ApiResponse_TaskStartResult_":{"properties":{"data":{"$ref":"#/components/schemas/TaskStartResult"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[TaskStartResult]"},"ApiResponse_TeamListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/TeamListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[TeamListPayload]"},"ApiResponse_TeamPayload_":{"properties":{"data":{"$ref":"#/components/schemas/TeamPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[TeamPayload]"},"ApiResponse_TokenResponse_":{"properties":{"data":{"$ref":"#/components/schemas/TokenResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[TokenResponse]"},"ApiResponse_TrendsDTO_":{"properties":{"data":{"$ref":"#/components/schemas/TrendsDTO"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[TrendsDTO]"},"ApiResponse_Union_AppLimitResponse__NoneType__":{"properties":{"data":{"anyOf":[{"$ref":"#/components/schemas/AppLimitResponse"},{"type":"null"}]},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[Union[AppLimitResponse, NoneType]]"},"ApiResponse_Union_DeploymentResponse__NoneType__":{"properties":{"data":{"anyOf":[{"$ref":"#/components/schemas/DeploymentResponse"},{"type":"null"}]},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[Union[DeploymentResponse, NoneType]]"},"ApiResponse_Union_DeskBatch__NoneType__":{"properties":{"data":{"anyOf":[{"$ref":"#/components/schemas/DeskBatch"},{"type":"null"}]},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[Union[DeskBatch, NoneType]]"},"ApiResponse_Union_SavedViewResponse__NoneType__":{"properties":{"data":{"anyOf":[{"$ref":"#/components/schemas/SavedViewResponse"},{"type":"null"}]},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[Union[SavedViewResponse, NoneType]]"},"ApiResponse_UnsuppressActionResponse_":{"properties":{"data":{"$ref":"#/components/schemas/UnsuppressActionResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[UnsuppressActionResponse]"},"ApiResponse_UsageBalanceResponse_":{"properties":{"data":{"$ref":"#/components/schemas/UsageBalanceResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[UsageBalanceResponse]"},"ApiResponse_UsageSummaryResponse_":{"properties":{"data":{"$ref":"#/components/schemas/UsageSummaryResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[UsageSummaryResponse]"},"ApiResponse_ValidateManifestResponse_":{"properties":{"data":{"$ref":"#/components/schemas/ValidateManifestResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[ValidateManifestResponse]"},"ApiResponse_VerifyEmailResponse_":{"properties":{"data":{"$ref":"#/components/schemas/VerifyEmailResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[VerifyEmailResponse]"},"ApiResponse_VisitorCompanyResponse_":{"properties":{"data":{"$ref":"#/components/schemas/VisitorCompanyResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[VisitorCompanyResponse]"},"ApiResponse_VisitorContactEvents_":{"properties":{"data":{"$ref":"#/components/schemas/VisitorContactEvents"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[VisitorContactEvents]"},"ApiResponse_VisitorEventPage_":{"properties":{"data":{"$ref":"#/components/schemas/VisitorEventPage"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[VisitorEventPage]"},"ApiResponse_VisitorListSyncJob_":{"properties":{"data":{"$ref":"#/components/schemas/VisitorListSyncJob"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[VisitorListSyncJob]"},"ApiResponse_VisitorScoreResponse_":{"properties":{"data":{"$ref":"#/components/schemas/VisitorScoreResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[VisitorScoreResponse]"},"ApiResponse_VisitorStatisticsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/VisitorStatisticsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[VisitorStatisticsResponse]"},"ApiResponse_VisitorStreamsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/VisitorStreamsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[VisitorStreamsResponse]"},"ApiResponse_VoiceAgentListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/VoiceAgentListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[VoiceAgentListResponse]"},"ApiResponse_VoiceAgentResponse_":{"properties":{"data":{"$ref":"#/components/schemas/VoiceAgentResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[VoiceAgentResponse]"},"ApiResponse_VoiceCallStartResponse_":{"properties":{"data":{"$ref":"#/components/schemas/VoiceCallStartResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[VoiceCallStartResponse]"},"ApiResponse_VoiceCustomDispositionItem_":{"properties":{"data":{"$ref":"#/components/schemas/VoiceCustomDispositionItem"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[VoiceCustomDispositionItem]"},"ApiResponse_VoiceDispositionListResponse_":{"properties":{"data":{"$ref":"#/components/schemas/VoiceDispositionListResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[VoiceDispositionListResponse]"},"ApiResponse_VoiceListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/VoiceListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[VoiceListPayload]"},"ApiResponse_VoicePayload_":{"properties":{"data":{"$ref":"#/components/schemas/VoicePayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[VoicePayload]"},"ApiResponse_WaterfallConfigsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/WaterfallConfigsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WaterfallConfigsResponse]"},"ApiResponse_WebchatListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/WebchatListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WebchatListPayload]"},"ApiResponse_WebchatPayload_":{"properties":{"data":{"$ref":"#/components/schemas/WebchatPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WebchatPayload]"},"ApiResponse_WebhookResponse_":{"properties":{"data":{"$ref":"#/components/schemas/WebhookResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WebhookResponse]"},"ApiResponse_WebsiteEditorConnection_":{"properties":{"data":{"$ref":"#/components/schemas/WebsiteEditorConnection"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WebsiteEditorConnection]"},"ApiResponse_WorkActivityPage_":{"properties":{"data":{"$ref":"#/components/schemas/WorkActivityPage"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkActivityPage]"},"ApiResponse_WorkAgentArchived_":{"properties":{"data":{"$ref":"#/components/schemas/WorkAgentArchived"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkAgentArchived]"},"ApiResponse_WorkAgentCreated_":{"properties":{"data":{"$ref":"#/components/schemas/WorkAgentCreated"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkAgentCreated]"},"ApiResponse_WorkAgentExecutionIdentities_":{"properties":{"data":{"$ref":"#/components/schemas/WorkAgentExecutionIdentities"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkAgentExecutionIdentities]"},"ApiResponse_WorkAgentPolicy_":{"properties":{"data":{"$ref":"#/components/schemas/WorkAgentPolicy"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkAgentPolicy]"},"ApiResponse_WorkAgentProfilePage_":{"properties":{"data":{"$ref":"#/components/schemas/WorkAgentProfilePage"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkAgentProfilePage]"},"ApiResponse_WorkAgentProfile_":{"properties":{"data":{"$ref":"#/components/schemas/WorkAgentProfile"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkAgentProfile]"},"ApiResponse_WorkAttachmentLink_":{"properties":{"data":{"$ref":"#/components/schemas/WorkAttachmentLink"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkAttachmentLink]"},"ApiResponse_WorkAvailableChannelList_":{"properties":{"data":{"$ref":"#/components/schemas/WorkAvailableChannelList"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkAvailableChannelList]"},"ApiResponse_WorkCanvas_":{"properties":{"data":{"$ref":"#/components/schemas/WorkCanvas"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkCanvas]"},"ApiResponse_WorkChannelList_":{"properties":{"data":{"$ref":"#/components/schemas/WorkChannelList"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkChannelList]"},"ApiResponse_WorkChannelPayload_":{"properties":{"data":{"$ref":"#/components/schemas/WorkChannelPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkChannelPayload]"},"ApiResponse_WorkChannelWriteResult_":{"properties":{"data":{"$ref":"#/components/schemas/WorkChannelWriteResult"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkChannelWriteResult]"},"ApiResponse_WorkCustomEmojiResult_":{"properties":{"data":{"$ref":"#/components/schemas/WorkCustomEmojiResult"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkCustomEmojiResult]"},"ApiResponse_WorkDailyBriefSettings_":{"properties":{"data":{"$ref":"#/components/schemas/WorkDailyBriefSettings"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkDailyBriefSettings]"},"ApiResponse_WorkEventPage_":{"properties":{"data":{"$ref":"#/components/schemas/WorkEventPage"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkEventPage]"},"ApiResponse_WorkInboxDisposition_":{"properties":{"data":{"$ref":"#/components/schemas/WorkInboxDisposition"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkInboxDisposition]"},"ApiResponse_WorkInboxDispositions_":{"properties":{"data":{"$ref":"#/components/schemas/WorkInboxDispositions"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkInboxDispositions]"},"ApiResponse_WorkItemList_":{"properties":{"data":{"$ref":"#/components/schemas/WorkItemList"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkItemList]"},"ApiResponse_WorkMemoryNote_":{"properties":{"data":{"$ref":"#/components/schemas/WorkMemoryNote"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkMemoryNote]"},"ApiResponse_WorkMemoryPage_":{"properties":{"data":{"$ref":"#/components/schemas/WorkMemoryPage"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkMemoryPage]"},"ApiResponse_WorkMessagePage_":{"properties":{"data":{"$ref":"#/components/schemas/WorkMessagePage"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkMessagePage]"},"ApiResponse_WorkMessage_":{"properties":{"data":{"$ref":"#/components/schemas/WorkMessage"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkMessage]"},"ApiResponse_WorkOversight_":{"properties":{"data":{"$ref":"#/components/schemas/WorkOversight"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkOversight]"},"ApiResponse_WorkProjectDeleted_":{"properties":{"data":{"$ref":"#/components/schemas/WorkProjectDeleted"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkProjectDeleted]"},"ApiResponse_WorkProjectWriteResult_":{"properties":{"data":{"$ref":"#/components/schemas/WorkProjectWriteResult"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkProjectWriteResult]"},"ApiResponse_WorkPulseNote_":{"properties":{"data":{"$ref":"#/components/schemas/WorkPulseNote"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkPulseNote]"},"ApiResponse_WorkPulseReaction_":{"properties":{"data":{"$ref":"#/components/schemas/WorkPulseReaction"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkPulseReaction]"},"ApiResponse_WorkReadMarkers_":{"properties":{"data":{"$ref":"#/components/schemas/WorkReadMarkers"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkReadMarkers]"},"ApiResponse_WorkRoom_":{"properties":{"data":{"$ref":"#/components/schemas/WorkRoom"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkRoom]"},"ApiResponse_WorkRoutineDeleted_":{"properties":{"data":{"$ref":"#/components/schemas/WorkRoutineDeleted"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkRoutineDeleted]"},"ApiResponse_WorkRoutineEnvelope_":{"properties":{"data":{"$ref":"#/components/schemas/WorkRoutineEnvelope"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkRoutineEnvelope]"},"ApiResponse_WorkRoutineList_":{"properties":{"data":{"$ref":"#/components/schemas/WorkRoutineList"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkRoutineList]"},"ApiResponse_WorkRoutineRunList_":{"properties":{"data":{"$ref":"#/components/schemas/WorkRoutineRunList"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkRoutineRunList]"},"ApiResponse_WorkRoutineRunResult_":{"properties":{"data":{"$ref":"#/components/schemas/WorkRoutineRunResult"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkRoutineRunResult]"},"ApiResponse_WorkSearchResults_":{"properties":{"data":{"$ref":"#/components/schemas/WorkSearchResults"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkSearchResults]"},"ApiResponse_WorkSidebarPreferences_":{"properties":{"data":{"$ref":"#/components/schemas/WorkSidebarPreferences"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkSidebarPreferences]"},"ApiResponse_WorkSignalPromoted_":{"properties":{"data":{"$ref":"#/components/schemas/WorkSignalPromoted"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkSignalPromoted]"},"ApiResponse_WorkSignalState_":{"properties":{"data":{"$ref":"#/components/schemas/WorkSignalState"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkSignalState]"},"ApiResponse_WorkTeamHqHistory_":{"properties":{"data":{"$ref":"#/components/schemas/WorkTeamHqHistory"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkTeamHqHistory]"},"ApiResponse_WorkTeamHqLeaderboard_":{"properties":{"data":{"$ref":"#/components/schemas/WorkTeamHqLeaderboard"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkTeamHqLeaderboard]"},"ApiResponse_WorkTickerEvents_":{"properties":{"data":{"$ref":"#/components/schemas/WorkTickerEvents"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkTickerEvents]"},"ApiResponse_WorkbenchPage_":{"properties":{"data":{"$ref":"#/components/schemas/WorkbenchPage"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkbenchPage]"},"ApiResponse_WorkbenchTableList_":{"properties":{"data":{"$ref":"#/components/schemas/WorkbenchTableList"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkbenchTableList]"},"ApiResponse_WorkbenchTable_":{"properties":{"data":{"$ref":"#/components/schemas/WorkbenchTable"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkbenchTable]"},"ApiResponse_WorkflowTriggerObjectsResponse_":{"properties":{"data":{"$ref":"#/components/schemas/WorkflowTriggerObjectsResponse"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkflowTriggerObjectsResponse]"},"ApiResponse_WorkspaceSearchListPayload_":{"properties":{"data":{"$ref":"#/components/schemas/WorkspaceSearchListPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkspaceSearchListPayload]"},"ApiResponse_WorkspaceSearchPayload_":{"properties":{"data":{"$ref":"#/components/schemas/WorkspaceSearchPayload"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[WorkspaceSearchPayload]"},"ApiResponse_dict_":{"properties":{"data":{"additionalProperties":true,"type":"object","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[dict]"},"ApiResponse_dict_str__Any__":{"properties":{"data":{"additionalProperties":true,"type":"object","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[dict[str, Any]]"},"ApiResponse_dict_str__int__":{"properties":{"data":{"additionalProperties":{"type":"integer"},"type":"object","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[dict[str, int]]"},"ApiResponse_dict_str__list_FilterOptionItem___":{"properties":{"data":{"additionalProperties":{"items":{"$ref":"#/components/schemas/FilterOptionItem"},"type":"array"},"type":"object","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[dict[str, list[FilterOptionItem]]]"},"ApiResponse_list_":{"properties":{"data":{"items":{},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list]"},"ApiResponse_list_AdCampaignResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/AdCampaignResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[AdCampaignResponse]]"},"ApiResponse_list_AgentApprovalResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/AgentApprovalResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[AgentApprovalResponse]]"},"ApiResponse_list_AppPageResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/AppPageResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[AppPageResponse]]"},"ApiResponse_list_AppResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/AppResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[AppResponse]]"},"ApiResponse_list_AppSecretResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/AppSecretResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[AppSecretResponse]]"},"ApiResponse_list_AppointmentHostGroup__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/AppointmentHostGroup"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[AppointmentHostGroup]]"},"ApiResponse_list_AppointmentLimitHistoryEntry__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/AppointmentLimitHistoryEntry"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[AppointmentLimitHistoryEntry]]"},"ApiResponse_list_AttributeDefinitionResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/AttributeDefinitionResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[AttributeDefinitionResponse]]"},"ApiResponse_list_AudienceSyncConfigResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/AudienceSyncConfigResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[AudienceSyncConfigResponse]]"},"ApiResponse_list_Column__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/Column"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[Column]]"},"ApiResponse_list_CompanyContactItem__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/CompanyContactItem"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[CompanyContactItem]]"},"ApiResponse_list_CompanyListItem__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/CompanyListItem"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[CompanyListItem]]"},"ApiResponse_list_ContactDealResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/ContactDealResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[ContactDealResponse]]"},"ApiResponse_list_ContactListItem__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/ContactListItem"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[ContactListItem]]"},"ApiResponse_list_CredentialResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/CredentialResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[CredentialResponse]]"},"ApiResponse_list_CrmIntegrationResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/CrmIntegrationResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[CrmIntegrationResponse]]"},"ApiResponse_list_DealResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/DealResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[DealResponse]]"},"ApiResponse_list_DeploymentResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/DeploymentResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[DeploymentResponse]]"},"ApiResponse_list_DomainResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/DomainResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[DomainResponse]]"},"ApiResponse_list_FieldResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/FieldResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[FieldResponse]]"},"ApiResponse_list_InboxThreadResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/InboxThreadResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[InboxThreadResponse]]"},"ApiResponse_list_InstallationResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/InstallationResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[InstallationResponse]]"},"ApiResponse_list_InstalledAppResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/InstalledAppResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[InstalledAppResponse]]"},"ApiResponse_list_LifecycleRecordItem__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/LifecycleRecordItem"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[LifecycleRecordItem]]"},"ApiResponse_list_LifecycleStageResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/LifecycleStageResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[LifecycleStageResponse]]"},"ApiResponse_list_ListResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/ListResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[ListResponse]]"},"ApiResponse_list_MeetingSummary__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/MeetingSummary"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[MeetingSummary]]"},"ApiResponse_list_NoteResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/NoteResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[NoteResponse]]"},"ApiResponse_list_ObjectBoardGroup__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/ObjectBoardGroup"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[ObjectBoardGroup]]"},"ApiResponse_list_ObjectDefinitionResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/ObjectDefinitionResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[ObjectDefinitionResponse]]"},"ApiResponse_list_ObjectImportSummary__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/ObjectImportSummary"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[ObjectImportSummary]]"},"ApiResponse_list_ObjectRecordResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/ObjectRecordResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[ObjectRecordResponse]]"},"ApiResponse_list_OpsActionRow__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/OpsActionRow"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[OpsActionRow]]"},"ApiResponse_list_OpsActionSummaryRow__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/OpsActionSummaryRow"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[OpsActionSummaryRow]]"},"ApiResponse_list_OpsWebhookEventSummary__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/OpsWebhookEventSummary"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[OpsWebhookEventSummary]]"},"ApiResponse_list_PipelineResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/PipelineResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[PipelineResponse]]"},"ApiResponse_list_PipelineStageResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/PipelineStageResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[PipelineStageResponse]]"},"ApiResponse_list_QuoteDetail__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/QuoteDetail"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[QuoteDetail]]"},"ApiResponse_list_RepoResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/RepoResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[RepoResponse]]"},"ApiResponse_list_RequestLogEntry__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/RequestLogEntry"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[RequestLogEntry]]"},"ApiResponse_list_SavedViewResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SavedViewResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[SavedViewResponse]]"},"ApiResponse_list_SchemaVersionResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SchemaVersionResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[SchemaVersionResponse]]"},"ApiResponse_list_SearchCompanyItem__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SearchCompanyItem"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[SearchCompanyItem]]"},"ApiResponse_list_SearchContactItem__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SearchContactItem"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[SearchContactItem]]"},"ApiResponse_list_SequenceContactItem__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SequenceContactItem"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[SequenceContactItem]]"},"ApiResponse_list_SequenceListItem__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SequenceListItem"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[SequenceListItem]]"},"ApiResponse_list_SignatureAssignmentResult__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SignatureAssignmentResult"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[SignatureAssignmentResult]]"},"ApiResponse_list_SignatureCampaignResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SignatureCampaignResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[SignatureCampaignResponse]]"},"ApiResponse_list_SignatureMember__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SignatureMember"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[SignatureMember]]"},"ApiResponse_list_SignatureTemplateResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SignatureTemplateResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[SignatureTemplateResponse]]"},"ApiResponse_list_StreamInfoResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/StreamInfoResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[StreamInfoResponse]]"},"ApiResponse_list_SuppressionRecord__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SuppressionRecord"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[SuppressionRecord]]"},"ApiResponse_list_SurveyResponseDTO__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SurveyResponseDTO"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[SurveyResponseDTO]]"},"ApiResponse_list_SurveySendingDomainDTO__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SurveySendingDomainDTO"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[SurveySendingDomainDTO]]"},"ApiResponse_list_SurveyTriggerDTO__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SurveyTriggerDTO"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[SurveyTriggerDTO]]"},"ApiResponse_list_SyncErrorResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SyncErrorResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[SyncErrorResponse]]"},"ApiResponse_list_SyncRunResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/SyncRunResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[SyncRunResponse]]"},"ApiResponse_list_TaskResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/TaskResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[TaskResponse]]"},"ApiResponse_list_UsageTransactionResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/UsageTransactionResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[UsageTransactionResponse]]"},"ApiResponse_list_WebhookDeliveryResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/WebhookDeliveryResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[WebhookDeliveryResponse]]"},"ApiResponse_list_WebhookEventResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/WebhookEventResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[WebhookEventResponse]]"},"ApiResponse_list_WebhookResponse__":{"properties":{"data":{"items":{"$ref":"#/components/schemas/WebhookResponse"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[WebhookResponse]]"},"ApiResponse_list_dict__":{"properties":{"data":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[dict]]"},"ApiResponse_list_dict_str__Any___":{"properties":{"data":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[dict[str, Any]]]"},"ApiResponse_list_str__":{"properties":{"data":{"items":{"type":"string"},"type":"array","title":"Data"},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ApiResponse[list[str]]"},"AppLimitResponse":{"properties":{"app_id":{"type":"string","title":"App Id"},"window":{"type":"string","title":"Window","description":"Cap window. `calendar_month` today."},"credit_cap":{"type":"integer","title":"Credit Cap"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"}},"type":"object","required":["app_id","window","credit_cap"],"title":"AppLimitResponse","description":"An app's hard credit cap. Mirrors `AppLimitDto`.\n\nThe endpoint returns `null` for no cap. There is no \"unlimited\" sentinel, so\nan accidental zero can never read as no limit."},"AppLogsResponse":{"properties":{"app_id":{"type":"string","title":"App Id"},"deployment_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Deployment Id","description":"Set for build logs. `null` for the running app's logs."},"namespace":{"type":"string","title":"Namespace","description":"The app's own Kubernetes namespace. Derived from the app id, never supplied."},"tail_lines":{"type":"integer","title":"Tail Lines","description":"Lines requested per container, after clamping to the server maximum."},"redacted":{"type":"boolean","title":"Redacted","default":true},"containers":{"items":{"$ref":"#/components/schemas/ContainerLogResponse"},"type":"array","title":"Containers"}},"type":"object","required":["app_id","namespace","tail_lines"],"title":"AppLogsResponse","description":"Logs for one app or one of its builds.\n\n``redacted`` is always true and means only that graph8's credential patterns\nwere applied. It is NOT a claim the output is safe to publish: these are a\ncustomer's own build and application logs, and an application can print a\nsecret in a shape no pattern matches."},"AppPageActionsResponse":{"properties":{"page_id":{"type":"string","title":"Page Id"},"actions_by_alias":{"additionalProperties":{"items":{"$ref":"#/components/schemas/ActionDescriptorDto"},"type":"array"},"type":"object","title":"Actions By Alias"}},"type":"object","required":["page_id"],"title":"AppPageActionsResponse","description":"Everything this page can do, grouped by the alias it acts on.\n\nOnly aliases the page actually binds appear. An action is addressed by\n(alias, name), never by a source id, which is what stops a page acting on\nsomething it does not bind."},"AppPageArtifactResponse":{"properties":{"page_id":{"type":"string","title":"Page Id"},"name":{"type":"string","title":"Name"},"status":{"type":"string","title":"Status"},"html_source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Html Source"},"data_manifest":{"additionalProperties":true,"type":"object","title":"Data Manifest"},"updated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["page_id","name","status"],"title":"AppPageArtifactResponse","description":"The generated page itself, plus the manifest wiring it to its sources."},"AppPageChatEditRequest":{"properties":{"instruction":{"type":"string","maxLength":2000,"minLength":1,"title":"Instruction"}},"type":"object","required":["instruction"],"title":"AppPageChatEditRequest"},"AppPageChatEditResponse":{"properties":{"page_id":{"type":"string","title":"Page Id"},"status":{"type":"string","title":"Status","default":"ready"},"version_num":{"type":"integer","title":"Version Num"},"edit_summary":{"type":"string","title":"Edit Summary"}},"type":"object","required":["page_id","version_num","edit_summary"],"title":"AppPageChatEditResponse"},"AppPageFrameSessionResponse":{"properties":{"token":{"type":"string","title":"Token"},"view_session_id":{"type":"string","title":"View Session Id"},"expires_in":{"type":"integer","title":"Expires In"},"frame_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Frame Url","description":"Absolute URL to load, token included. Absent when no frame origin is configured."}},"type":"object","required":["token","view_session_id","expires_in"],"title":"AppPageFrameSessionResponse","description":"A one-shot token for loading the page's sandboxed frame.\n\nSingle use and short lived. The frame is served from a cookieless origin\nunder a `default-src 'none'` policy, so this token is the only thing that\nauthorizes a load."},"AppPageResponse":{"properties":{"page_id":{"type":"string","title":"Page Id"},"name":{"type":"string","title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"sources":{"items":{"$ref":"#/components/schemas/AppPageSourceDto"},"type":"array","title":"Sources"},"status":{"type":"string","title":"Status","description":"draft | generating | ready | failed"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["page_id","name","status"],"title":"AppPageResponse"},"AppPageRestoreResponse":{"properties":{"page_id":{"type":"string","title":"Page Id"},"restored_from_version":{"type":"integer","title":"Restored From Version"},"snapshot_version":{"type":"integer","title":"Snapshot Version"}},"type":"object","required":["page_id","restored_from_version","snapshot_version"],"title":"AppPageRestoreResponse"},"AppPageSourceCatalogPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"AppPageSourceCatalogPayload","description":"Source families or instances under `items`."},"AppPageSourceDto":{"properties":{"source_kind":{"type":"string","title":"Source Kind","description":"Connector family, e.g. staging-table or custom-object"},"source_id":{"type":"string","title":"Source Id","description":"Opaque to everything but the connector that owns it"},"alias":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Alias","description":"Handle used inside the page. Auto-assigned from the kind when omitted."},"role":{"type":"string","title":"Role","default":"data"},"position":{"type":"integer","title":"Position","default":0}},"type":"object","required":["source_kind","source_id"],"title":"AppPageSourceDto","description":"One data source bound into a page. `alias` is the handle the generated\npage's JavaScript addresses it by."},"AppPageSourcesPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"AppPageSourcesPayload","description":"The page after its sources changed."},"AppPageSourcesReplaceRequest":{"properties":{"sources":{"items":{"$ref":"#/components/schemas/AppPageSourceDto"},"type":"array","minItems":1,"title":"Sources","description":"The page's full source list."}},"type":"object","required":["sources"],"title":"AppPageSourcesReplaceRequest"},"AppPageStatusResponse":{"properties":{"page_id":{"type":"string","title":"Page Id"},"status":{"type":"string","title":"Status"},"has_page":{"type":"boolean","title":"Has Page","description":"True once generation has stored HTML. `status: ready` alone is not enough.","default":false}},"type":"object","required":["page_id","status"],"title":"AppPageStatusResponse"},"AppPageVersionDto":{"properties":{"version_num":{"type":"integer","title":"Version Num"},"edit_instruction":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Edit Instruction"},"edit_summary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Edit Summary"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"}},"type":"object","required":["version_num"],"title":"AppPageVersionDto"},"AppPageVersionListResponse":{"properties":{"page_id":{"type":"string","title":"Page Id"},"versions":{"items":{"$ref":"#/components/schemas/AppPageVersionDto"},"type":"array","title":"Versions"}},"type":"object","required":["page_id"],"title":"AppPageVersionListResponse"},"AppResponse":{"properties":{"app_id":{"type":"string","title":"App Id"},"builder_org_id":{"type":"string","title":"Builder Org Id"},"slug":{"type":"string","title":"Slug"},"name":{"type":"string","title":"Name"},"status":{"type":"string","title":"Status","description":"Lifecycle state: `draft`, `published`, `suspended` or `archived`. `active` is accepted on write as a legacy spelling of `published`."},"registered_origins":{"items":{"type":"string"},"type":"array","title":"Registered Origins","description":"https-only origins a browser app token may be presented from."},"default_hostname":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Default Hostname"},"source_repo_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Repo Url","description":"Where this app's code lives. Null until bound."},"source_provider":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Provider"},"source_default_branch":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Default Branch"},"source_credential_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Credential Ref","description":"A POINTER to the credential (a secret-manager path), never the credential itself."},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"archived_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Archived At"}},"type":"object","required":["app_id","builder_org_id","slug","name","status"],"title":"AppResponse","description":"One builder-owned app. Mirrors `AppDto`."},"AppRuntimeResponse":{"properties":{"app_id":{"type":"string","title":"App Id"},"ready":{"type":"boolean","title":"Ready","description":"True only when nothing in `blockers` remains. False is the normal answer today."},"source_bound":{"type":"boolean","title":"Source Bound"},"hostname_assigned":{"type":"boolean","title":"Hostname Assigned"},"secrets_declared":{"type":"integer","title":"Secrets Declared"},"latest_deployment_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Latest Deployment Status"},"blockers":{"items":{"type":"string"},"type":"array","title":"Blockers","description":"Each unmet prerequisite, named. Empty means ready."}},"type":"object","required":["app_id","ready","source_bound","hostname_assigned","secrets_declared"],"title":"AppRuntimeResponse","description":"Whether an app is ready to be built and run, and what is missing (J9).\n\nA READINESS REPORT, not a promise. It answers from what the control plane\nknows: is a source bound, is a hostname assigned, are secrets declared, what\ndid the last deployment do. It does NOT claim the cluster side is ready,\nbecause the namespace provisioner, the image registry and the runtime objects\nare separate work and none of them exist yet.\n\n`blockers` is the useful field and it is deliberately explicit. An agent\ndriving a build needs to know WHY it cannot proceed, and a bare\n`ready: false` sends it guessing."},"AppSecretResponse":{"properties":{"secret_key":{"type":"string","title":"Secret Key"},"provider_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Provider Ref","description":"Where the value lives, e.g. a secret-manager path. Never the value."},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"rotated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Rotated At","description":"Last time this declaration was rewritten. Moves on every write, including one that repeats the same pointer: the pointer is not the secret, so an unchanged path does not mean an unchanged value."}},"type":"object","required":["secret_key"],"title":"AppSecretResponse","description":"One declared secret. A POINTER and two timestamps, never a value.\n\nThere is no `value` field and there must never be one. The control plane\nstores WHICH secrets an app declares and where they live, so a build can be\nrendered without the platform ever holding what the build will read."},"AppSourceRequest":{"properties":{"repo_url":{"type":"string","maxLength":2000,"minLength":1,"title":"Repo Url","description":"Clone URL."},"provider":{"type":"string","title":"Provider","description":"One of: github, gitlab, bitbucket."},"default_branch":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Default Branch","description":"Defaults to the repository's own default when omitted."},"credential_ref":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Credential Ref","description":"Secret-manager PATH for the fetch credential. Never the credential itself."}},"type":"object","required":["repo_url","provider"],"title":"AppSourceRequest","description":"Bind an app to the repository a build should fetch (J1).\n\nPROVIDER IS VALIDATED HERE, NOT BY A CHECK CONSTRAINT. `ensure_public_tables`\nemits `ADD COLUMN IF NOT EXISTS`, which cannot add a CHECK to an already\ncreated table, and editing the constraint tuple alone is a silent no-op. So\nthe vocabulary lives in `SOURCE_PROVIDERS` and this DTO is what enforces it,\nthe same way `repos_router` already validates its provider.\n\n`credential_ref` is a POINTER, and the description says so on the wire. A\nbuilder who pastes a token here has put it in the control-plane row, in every\nbackup of it, and in the response body of `GET /apps/{app_id}`. There is no\nway to un-send that, so the field is named and documented to make the mistake\nhard rather than merely regrettable."},"AppUserResponseRowDTO":{"properties":{"app_user_id":{"type":"string","title":"App User Id"},"score":{"type":"integer","title":"Score"},"channel":{"type":"string","title":"Channel"},"responded_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Responded At"},"comment":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Comment"}},"type":"object","required":["app_user_id","score","channel"],"title":"AppUserResponseRowDTO"},"AppUserResponsesDTO":{"properties":{"survey_id":{"type":"string","title":"Survey Id"},"responses":{"items":{"$ref":"#/components/schemas/AppUserResponseRowDTO"},"type":"array","title":"Responses"}},"type":"object","required":["survey_id","responses"],"title":"AppUserResponsesDTO"},"ApplicationPatch":{"properties":{"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"hiring_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Hiring Id"}},"type":"object","title":"ApplicationPatch"},"ApplyFindingsRequest":{"properties":{"finding_ids":{"items":{"type":"string"},"type":"array","title":"Finding Ids"}},"type":"object","required":["finding_ids"],"title":"ApplyFindingsRequest","description":"Apply review findings DETERMINISTICALLY. Spends nothing."},"ApplyManifestResponse":{"properties":{"app_id":{"type":"string","title":"App Id"},"summary":{"$ref":"#/components/schemas/ManifestSummary"},"schema_version":{"anyOf":[{"$ref":"#/components/schemas/SchemaVersionResponse"},{"type":"null"}]},"schema_created":{"type":"boolean","title":"Schema Created","description":"False when an identical schema was already published. The version named above exists either way; this is what says nothing changed.","default":false},"materialization":{"anyOf":[{"$ref":"#/components/schemas/MaterializationSummary"},{"type":"null"}]},"deploy_config_stored":{"type":"boolean","title":"Deploy Config Stored","default":false}},"type":"object","required":["app_id","summary"],"title":"ApplyManifestResponse","description":"What an apply actually did, part by part.\n\nEach field answers \"did this half happen\", because a manifest declaring only\n`objects:` and one declaring only `backend:` are both legal and do different\namounts of work. A caller should never have to infer that from a 200."},"ApplyResponse":{"properties":{"status":{"type":"string","title":"Status"},"patch_count":{"type":"integer","title":"Patch Count"}},"type":"object","required":["status","patch_count"],"title":"ApplyResponse"},"AppointmentHost":{"properties":{"user_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"User Id"},"event_type_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Event Type Id"},"is_fixed":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Fixed","description":"True = on EVERY booking. False = one of the round-robin rotation. This is the setting that decides who actually gets booked."},"priority":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Priority","description":"Rotation priority."},"weight":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Weight","description":"Relative share of the rotation."},"schedule_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Schedule Id","description":"Availability schedule this host is booked against."},"group_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Group Id","description":"Host group, if partitioned."},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"},"avatar_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Avatar Url"}},"additionalProperties":true,"type":"object","title":"AppointmentHost","description":"One person bookable on an event type."},"AppointmentHostBookingLimitsRequest":{"properties":{"frequency":{"anyOf":[{"$ref":"#/components/schemas/HostLimitKindRequest"},{"type":"null"}]},"duration":{"anyOf":[{"$ref":"#/components/schemas/HostLimitKindRequest"},{"type":"null"}]}},"additionalProperties":false,"type":"object","title":"AppointmentHostBookingLimitsRequest","description":"One host's own booking limit on a team event: per kind, inherit the default, a custom value, or none."},"AppointmentHostCreateRequest":{"properties":{"user_id":{"type":"integer","title":"User Id","description":"User to add as a host."},"is_fixed":{"type":"boolean","title":"Is Fixed","description":"True = on every booking; false = one of the round-robin rotation.","default":false},"priority":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Priority"},"weight":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Weight"},"schedule_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Schedule Id"},"group_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Group Id"}},"type":"object","required":["user_id"],"title":"AppointmentHostCreateRequest"},"AppointmentHostGroup":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"event_type_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Event Type Id"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"}},"additionalProperties":true,"type":"object","title":"AppointmentHostGroup","description":"A partition of an event type's hosts, so the rotation picks within it."},"AppointmentHostGroupWriteRequest":{"properties":{"name":{"type":"string","minLength":1,"title":"Name","description":"Group name."}},"type":"object","required":["name"],"title":"AppointmentHostGroupWriteRequest"},"AppointmentHostUpdateRequest":{"properties":{"is_fixed":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Fixed"},"priority":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Priority"},"weight":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Weight"},"schedule_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Schedule Id"},"group_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Group Id"}},"type":"object","title":"AppointmentHostUpdateRequest","description":"Every field optional; omit one to leave it unchanged."},"AppointmentLimitHistoryEntry":{"properties":{"id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Id"},"actor_user_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Actor User Id"},"actor_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Actor Name"},"level":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Level","description":"`event`, `host_default` or `host_override`."},"target_user_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Target User Id"},"before":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Before"},"after":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"After"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"}},"additionalProperties":true,"type":"object","title":"AppointmentLimitHistoryEntry","description":"One change to an event type's booking limits."},"AppointmentLimitsPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"AppointmentLimitsPayload","description":"An event type after a booking-limit write, including its `limits_meta` (audit, permissions, time zone)."},"ApprovalChangeRequest":{"properties":{"feedback":{"type":"string","title":"Feedback","description":"Why the proposal is wrong, and what to do instead. REQUIRED and not decoration: it is stored on the rejection and is what the next plan is built from, so an empty-handed rejection produces the same plan again."}},"type":"object","required":["feedback"],"title":"ApprovalChangeRequest","description":"Mirror of `RequestChangesBody`."},"ApproveAllRequest":{"properties":{"lane":{"type":"string","title":"Lane","default":"now"}},"type":"object","title":"ApproveAllRequest"},"ApproveExecutionRequest":{"properties":{"decision":{"type":"string","enum":["approve","reject"],"title":"Decision","description":"Approve or reject the paused step."},"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason","description":"Recorded with a rejection."}},"type":"object","required":["decision"],"title":"ApproveExecutionRequest","description":"Mirrors `ApproveRequest`. The app refuses anything but these two decisions."},"ApproveOpportunityRequest":{"properties":{"content_types":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Content Types"},"kinds":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Kinds"},"seed_context":{"anyOf":[{"$ref":"#/components/schemas/SeedContext"},{"type":"null"}]},"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id"},"due_date":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"Due Date"},"create_crm_task":{"type":"boolean","title":"Create Crm Task","default":false}},"type":"object","title":"ApproveOpportunityRequest"},"ArchiveRequest":{"properties":{"is_archived":{"type":"boolean","title":"Is Archived"}},"type":"object","required":["is_archived"],"title":"ArchiveRequest","description":"Archive or UN-archive.\n\nAn explicit flag rather than a toggle, so a retried request is idempotent\ninstead of flipping the state back - and it is what makes the same route\nthe un-archive route."},"AsOf":{"properties":{"date":{"type":"string","format":"date","title":"Date"},"instant":{"type":"string","format":"date-time","title":"Instant"},"timezone":{"type":"string","title":"Timezone"}},"type":"object","required":["date","instant","timezone"],"title":"AsOf"},"AssessmentAnswerDef":{"properties":{"id":{"type":"string","maxLength":64,"minLength":1,"title":"Id"},"text":{"type":"string","maxLength":500,"minLength":1,"title":"Text"},"next_step_id":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Next Step Id"},"result_id":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Result Id"}},"type":"object","required":["id","text"],"title":"AssessmentAnswerDef","description":"A single selectable answer within an assessment step."},"AssessmentCreateRequest":{"properties":{"name":{"type":"string","maxLength":200,"minLength":1,"title":"Name"},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description"},"definition":{"$ref":"#/components/schemas/AssessmentDefinition","description":"The flow: `{start_step_id, steps[], results[]}`."},"surface":{"anyOf":[{"type":"string","enum":["external","internal"]},{"type":"null"}],"title":"Surface"}},"type":"object","required":["name","definition"],"title":"AssessmentCreateRequest","description":"A guided question flow the widget can run with a visitor.\n\n`definition` is the flow itself - a start step, the steps, and the results\nthey lead to. It is the app's own `AssessmentDefinition`, so a graph that\nnames a step it does not define is a 422 here rather than a dead end the\nvisitor walks into."},"AssessmentDefinition":{"properties":{"start_step_id":{"type":"string","maxLength":64,"minLength":1,"title":"Start Step Id"},"steps":{"items":{"$ref":"#/components/schemas/AssessmentStepDef"},"type":"array","title":"Steps"},"results":{"items":{"$ref":"#/components/schemas/AssessmentResultDef"},"type":"array","title":"Results"}},"type":"object","required":["start_step_id"],"title":"AssessmentDefinition","description":"Complete branching graph stored as JSONB in chat_assessments.definition."},"AssessmentResultDef":{"properties":{"id":{"type":"string","maxLength":64,"minLength":1,"title":"Id"},"title":{"type":"string","maxLength":200,"minLength":1,"title":"Title"},"body":{"type":"string","maxLength":2000,"title":"Body","default":""},"booking_enabled":{"type":"boolean","title":"Booking Enabled","default":false},"handoff_enabled":{"type":"boolean","title":"Handoff Enabled","default":false},"links":{"items":{"$ref":"#/components/schemas/AssessmentResultLink"},"type":"array","title":"Links"}},"type":"object","required":["id","title"],"title":"AssessmentResultDef","description":"A terminal result node — shown when the visitor's path leads here."},"AssessmentResultLink":{"properties":{"label":{"type":"string","maxLength":200,"minLength":1,"title":"Label"},"url":{"type":"string","maxLength":2048,"minLength":1,"title":"Url"}},"type":"object","required":["label","url"],"title":"AssessmentResultLink"},"AssessmentStepDef":{"properties":{"id":{"type":"string","maxLength":64,"minLength":1,"title":"Id"},"question":{"type":"string","maxLength":2000,"minLength":1,"title":"Question"},"answers":{"items":{"$ref":"#/components/schemas/AssessmentAnswerDef"},"type":"array","title":"Answers"},"allow_free_text":{"type":"boolean","title":"Allow Free Text","default":false}},"type":"object","required":["id","question"],"title":"AssessmentStepDef","description":"One question-and-answers step in the assessment flow."},"AssessmentUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":200,"minLength":1},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description"},"definition":{"anyOf":[{"$ref":"#/components/schemas/AssessmentDefinition"},{"type":"null"}]},"active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Active"},"surface":{"anyOf":[{"type":"string","enum":["external","internal"]},{"type":"null"}],"title":"Surface"},"revision":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Revision","description":"Revision you last read. See the note above on the name."}},"type":"object","title":"AssessmentUpdateRequest","description":"Partial edit of an assessment.\n\n`revision` is this model's optimistic-concurrency field. Note it is spelled\n`revision` here and `expected_revision` on every other webchat model - that\nis the app's own inconsistency, and it is mirrored rather than tidied,\nbecause renaming it would send the app a field it does not read and the\nconcurrency check would silently stop happening."},"AssignLinkedInAccountRequest":{"properties":{"provider":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Provider","description":"Which LinkedIn provider the account belongs to."},"account_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Ref","description":"The provider's own account key."},"linkedin_account_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Linkedin Account Id","description":"Legacy account id."}},"type":"object","title":"AssignLinkedInAccountRequest","description":"Attach a LinkedIn sending account. Mirrors `teams.AssignLinkedInAccountDTO`.\n\nAll three fields are optional because two spellings are supported: the\ncurrent `provider` + `account_ref` pair, and the legacy\n`linkedin_account_id`. The handler validates that one of them is usable."},"AssignListsRequest":{"properties":{"list_ids":{"items":{"type":"integer"},"type":"array","maxItems":200,"minItems":1,"title":"List Ids"}},"type":"object","required":["list_ids"],"title":"AssignListsRequest","description":"Make a configuration available on more lists."},"AssignManagedMemberRequest":{"properties":{"user_id":{"type":"integer","minimum":1.0,"title":"User Id","description":"The member's INTEGER scheduling user id - the `user_id` field of `GET /appointments/membership`. Not an email, not a PropelAuth id."}},"type":"object","required":["user_id"],"title":"AssignManagedMemberRequest","description":"Give one member their own bookable copy of a managed template."},"AssignObjectRequest":{"properties":{"object_id":{"type":"integer","title":"Object Id","description":"Integer id of the mailbox or phone number to attach."}},"type":"object","required":["object_id"],"title":"AssignObjectRequest","description":"Attach a mailbox or a phone number. Mirrors `teams.AssignObjectDTO`."},"AssignOwnerMatchingRequest":{"properties":{"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id","description":"Owner to assign. Null clears the owner on every match."},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id","description":"Restrict the selection to this list."},"filterModel":{"additionalProperties":true,"type":"object","title":"Filtermodel","description":"Per-column filters."},"segmentFilter":{"anyOf":[{"$ref":"#/components/schemas/SegmentFilterGroup"},{"type":"null"}],"description":"Advanced AND/OR filter tree."}},"type":"object","title":"AssignOwnerMatchingRequest","description":"Set the owner on every record matching a selection.\n\nA null `owner_id` UNASSIGNS the matching records rather than leaving them\nalone, so an omitted owner is a destructive instruction, not a no-op."},"AssignRequest":{"properties":{"assignee_email":{"type":"string","title":"Assignee Email","description":"Email of the user to assign"}},"type":"object","required":["assignee_email"],"title":"AssignRequest"},"AssignTeamCampaignRequest":{"properties":{"campaign_id":{"type":"string","title":"Campaign Id","description":"UUID of the campaign to link to this team."}},"type":"object","required":["campaign_id"],"title":"AssignTeamCampaignRequest","description":"Link a campaign to a team. Mirrors `teams.AssignTeamCampaignDTO`."},"AssignTeamRoleRequest":{"properties":{"slug":{"type":"string","enum":["ae","sdr","csm","campaign_manager","sales_manager"],"title":"Slug","description":"The role to grant. `admin` is not assignable here - it belongs to Settings -> Roles, behind the full RBAC admin gate."}},"type":"object","required":["slug"],"title":"AssignTeamRoleRequest","description":"Grant one Team HQ role to an existing member of the caller's org.\n\nA role REPLACES the person's whole permission set - `cb_user_roles` has a\ncomposite primary key on (user_id, org_id), so there is exactly one row per\nperson per org. This is a privilege grant, not a label."},"AssignmentCreateRequest":{"properties":{"assignee_emails":{"items":{"type":"string"},"type":"array","maxItems":20,"minItems":1,"title":"Assignee Emails","description":"Who owns this conversation. Check eligibility first."}},"type":"object","required":["assignee_emails"],"title":"AssignmentCreateRequest","description":"Give a conversation to one or more people.\n\nA LIST, and up to 20: the app models shared ownership rather than a single\nowner, so assigning replaces nothing - use `DELETE .../assign` to take\nsomeone off."},"AssociatedSequence":{"properties":{"id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Id"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"}},"additionalProperties":true,"type":"object","title":"AssociatedSequence"},"AsyncGenerateIdeasRequest":{"properties":{"organization_id":{"type":"string","title":"Organization Id","description":"Ignored for tenancy. The organisation is the API key's own."},"website_url":{"type":"string","title":"Website Url"},"campaign_goal":{"type":"string","title":"Campaign Goal"},"target_personas":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Target Personas"},"persona_mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Persona Mode","default":"selected"},"campaign_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Type","default":"all"},"num_ideas":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Num Ideas","description":"How many ideas to generate. Scales the spend.","default":5},"user_direction":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Direction"},"preferred_channels":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Preferred Channels"},"execution_targets":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Execution Targets"},"audience_source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience Source","default":"build_new"},"audience_list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Audience List Id"}},"type":"object","required":["organization_id","website_url","campaign_goal"],"title":"AsyncGenerateIdeasRequest","description":"The same generation, run in the background. SPENDS CREDIT.\n\nReturns a task id immediately. `num_ideas` is the cost multiplier."},"AttachedAsset":{"properties":{"type":{"type":"string","enum":["image","video"],"title":"Type","description":"Asset kind."},"id":{"type":"string","title":"Id","description":"Asset id."},"url":{"type":"string","title":"Url","description":"Public URL the generated page will reference."},"poster_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Poster Url","description":"Poster frame for a video."},"alt_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Alt Text","description":"Alt text."},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title","description":"Title."},"position_hint":{"type":"string","enum":["hero","body","any"],"title":"Position Hint","description":"Where the asset should land on the page.","default":"any"}},"type":"object","required":["type","id","url"],"title":"AttachedAsset","description":"Mirrors `campaign_builder.routers.brand_kit.AttachedAsset`.\n\nAn asset the generated page MUST use. Capped by the app at 5 images and 2\nvideos per submission; the cap is a model validator there, so it answers\n422 through the same path as any other body error."},"AttendeeInput":{"properties":{"name":{"type":"string","title":"Name"},"email":{"type":"string","title":"Email"},"time_zone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Time Zone"},"phone_number":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone Number"}},"type":"object","required":["name","email"],"title":"AttendeeInput"},"AttributeConfig":{"properties":{"referenced_object":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Referenced Object"},"target_object":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Object"},"options":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Options"},"currency_code":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Currency Code"},"max_value":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Max Value"},"formula":{"anyOf":[{"$ref":"#/components/schemas/FormulaInput"},{"type":"null"}]}},"type":"object","title":"AttributeConfig","description":"Configuration for specific attribute types."},"AttributeCreateRequest":{"properties":{"slug":{"type":"string","maxLength":100,"minLength":1,"pattern":"^[a-z][a-z0-9_]*$","title":"Slug"},"title":{"type":"string","maxLength":200,"minLength":1,"title":"Title"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"attribute_type":{"$ref":"#/components/schemas/AttributeType"},"is_multiselect":{"type":"boolean","title":"Is Multiselect","default":false},"is_unique":{"type":"boolean","title":"Is Unique","default":false},"is_required":{"type":"boolean","title":"Is Required","default":false},"is_default_value_enabled":{"type":"boolean","title":"Is Default Value Enabled","default":false},"default_value":{"anyOf":[{},{"type":"null"}],"title":"Default Value"},"config":{"anyOf":[{"$ref":"#/components/schemas/AttributeConfig"},{"type":"null"}]},"sort_order":{"type":"integer","title":"Sort Order","default":0}},"additionalProperties":false,"type":"object","required":["slug","title","attribute_type"],"title":"AttributeCreateRequest"},"AttributeDefinitionResponse":{"properties":{"slug":{"type":"string","title":"Slug","description":"Stable API slug for the attribute, used as a payload key."},"title":{"type":"string","title":"Title","description":"Customer-facing field label, distinct from its stable API slug."},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Customer-configured description of the field."},"sort_order":{"type":"integer","title":"Sort Order","description":"Configured display order; equal values are ordered by API slug.","default":0},"is_system":{"type":"boolean","title":"Is System","description":"Whether this field is protected as a system attribute.","default":false},"is_archived":{"type":"boolean","title":"Is Archived","description":"Archived fields retain their values and can be restored.","default":false},"attribute_type":{"type":"string","title":"Attribute Type","description":"One of the 16 supported attribute types (`text`, `number`, `email_address`, `timestamp`, `select`, `record_reference`, …). Determines how values are validated and canonicalized."},"is_required":{"type":"boolean","title":"Is Required","description":"Required on create. PATCH may omit it, but cannot clear it with null or an empty multivalue list.","default":false},"is_unique":{"type":"boolean","title":"Is Unique","description":"No two active records may hold the same value for this attribute. A collision is rejected with `409 duplicate_active_value`.","default":false},"is_multiselect":{"type":"boolean","title":"Is Multiselect","description":"Values are a list rather than a scalar.","default":false},"is_default_value_enabled":{"type":"boolean","title":"Is Default Value Enabled","description":"Apply the configured default when this field is omitted on create. Never applies on PATCH.","default":false},"default_value":{"title":"Default Value","description":"Configured create default. Enabled non-null defaults pass the same validation as explicit values."},"config":{"additionalProperties":true,"type":"object","title":"Config","description":"Type-specific configuration, e.g. select options. Record references require target_object and must resolve to active records in that object within the caller's organization and app."},"visible_to_role_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Visible To Role Ids","description":"Role ids that may see this field; null means every role. Owners and admins always see every field. A field hidden from the caller is absent from every response. Set it with PATCH on this attribute."}},"type":"object","required":["slug","title","attribute_type"],"title":"AttributeDefinitionResponse","description":"One field on a custom object, and the rules its values must satisfy."},"AttributeType":{"type":"string","enum":["text","number","currency","date","timestamp","checkbox","select","status","email_address","phone_number","domain","location","personal_name","record_reference","rating","actor_reference","formula"],"title":"AttributeType","description":"Valid attribute types for the Custom Objects type system."},"AttributeUpdateRequest":{"properties":{"title":{"anyOf":[{"type":"string","maxLength":200,"minLength":1},{"type":"null"}],"title":"Title"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"is_multiselect":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Multiselect"},"is_unique":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Unique"},"is_required":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Required"},"is_default_value_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Default Value Enabled"},"default_value":{"anyOf":[{},{"type":"null"}],"title":"Default Value"},"config":{"anyOf":[{"$ref":"#/components/schemas/AttributeConfig"},{"type":"null"}]},"sort_order":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Sort Order"},"is_archived":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Archived"},"visible_to_role_ids":{"anyOf":[{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":100},{"type":"null"}],"title":"Visible To Role Ids"}},"additionalProperties":false,"type":"object","title":"AttributeUpdateRequest"},"AudiencePipelineAcceptFiltersRequest":{"properties":{"filters":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Filters"},"list_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"List Name","description":"Custom list name (defaults to '{campaign_name} Audience')"},"run_pipeline":{"type":"boolean","title":"Run Pipeline","default":true}},"type":"object","required":["filters"],"title":"AudiencePipelineAcceptFiltersRequest","description":"Mirrors `AcceptFiltersRequest`.\n\n`run_pipeline` defaults to TRUE: accepting filters normally STARTS the run,\nwhich builds a list and can start a credit-spending enrichment. Send\n`false` to only save the filters."},"AudiencePipelineAcceptResult":{"properties":{"status":{"type":"string","title":"Status"},"campaign_id":{"type":"string","title":"Campaign Id"},"chain_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Chain Id"}},"type":"object","required":["status","campaign_id"],"title":"AudiencePipelineAcceptResult","description":"The app's answer to accepting filters: `status` is `filters_saved` when\n`run_pipeline` was false, `pipeline_started` (with a `chain_id`) otherwise."},"AudiencePipelineStatus":{"properties":{"pipeline_status":{"type":"string","title":"Pipeline Status","description":"Pipeline state: idle | suggested | extracting_filters | creating_list | provisioning_keywords | checking_enrichment | enriching | completed | failed","default":"idle"},"list_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"List Id"},"total_contacts":{"type":"integer","title":"Total Contacts","default":0},"enrichment_job_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Enrichment Job Id"},"keyword_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Keyword Ids"},"suggested_filters":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Suggested Filters"},"suggested_list_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Suggested List Name","description":"Pre-filled list name based on campaign name"},"error":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Error"},"started_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Started At"},"completed_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Completed At"}},"type":"object","title":"AudiencePipelineStatus","description":"Mirrors `AudiencePipelineStatusResponse`. Where the pipeline is, and what\nit has produced so far."},"AudiencePipelineSuggestedFilters":{"properties":{"filters":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Filters"},"source":{"type":"string","title":"Source","description":"Where filters came from: user_modified | targeting_doc"},"suggested_list_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Suggested List Name","description":"Pre-filled list name based on campaign name"}},"type":"object","required":["filters","source"],"title":"AudiencePipelineSuggestedFilters","description":"Mirrors `SuggestedFiltersResponse`. The targeting filters the pipeline\nwould build the list from, and where they came from."},"AudiencePipelineTriggerResult":{"properties":{"status":{"type":"string","title":"Status"},"chain_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Chain Id"},"campaign_id":{"type":"string","title":"Campaign Id"}},"type":"object","required":["status","campaign_id"],"title":"AudiencePipelineTriggerResult","description":"The app's answer to a trigger: `{\"status\": \"started\", \"chain_id\": ..., \"campaign_id\": ...}`."},"AudienceProfilePreviewRequest":{"properties":{"audience_id":{"type":"integer","title":"Audience Id"}},"type":"object","required":["audience_id"],"title":"AudienceProfilePreviewRequest","description":"Profile an audience list. Spends nothing."},"AudienceSyncConfigResponse":{"properties":{"id":{"type":"integer","title":"Id"},"audience_id":{"type":"integer","title":"Audience Id"},"platform":{"type":"string","title":"Platform"},"platform_audience_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Platform Audience Name"},"mode":{"type":"string","title":"Mode","default":"mirror"},"refresh_cadence_hours":{"type":"integer","title":"Refresh Cadence Hours","default":24},"is_active":{"type":"boolean","title":"Is Active","default":true},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"last_sync_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Sync At"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"status_reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status Reason","description":"Why the sync is not delivering, or null when healthy: keyword_only (no list, keyword-only Google Search; never scheduled), list_missing (every list it uploads from was deleted), lists_partially_missing, paused, failing (last run failed), failing_never_synced (has never succeeded)."},"status_detail":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status Detail","description":"Human-readable explanation of status_reason."},"last_sync_error":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Sync Error","description":"Error of the last failed run, if any."},"next_sync_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Next Sync At","description":"When the worker will next try this sync."}},"type":"object","required":["id","audience_id","platform"],"title":"AudienceSyncConfigResponse"},"AudienceSyncCreateRequest":{"properties":{"audience_id":{"type":"integer","exclusiveMinimum":0.0,"title":"Audience Id","description":"Audience list ID"},"platform":{"type":"string","title":"Platform","description":"Ad platform: meta | linkedin | google | x"},"platform_audience_name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Platform Audience Name"},"mode":{"type":"string","title":"Mode","description":"Sync mode: mirror | append_only","default":"mirror"},"refresh_cadence_hours":{"type":"integer","maximum":720.0,"minimum":0.0,"title":"Refresh Cadence Hours","default":24},"platform_config":{"additionalProperties":true,"type":"object","title":"Platform Config","description":"Platform-specific config (OAuth creds)"},"suppression_list_ids":{"items":{"type":"integer"},"type":"array","title":"Suppression List Ids"}},"type":"object","required":["audience_id","platform"],"title":"AudienceSyncCreateRequest"},"AudienceSyncUpdateRequest":{"properties":{"mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mode","description":"Sync mode: mirror | append_only"},"refresh_cadence_hours":{"anyOf":[{"type":"integer","maximum":720.0,"minimum":0.0},{"type":"null"}],"title":"Refresh Cadence Hours"},"is_active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Active"},"suppression_list_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Suppression List Ids"}},"type":"object","title":"AudienceSyncUpdateRequest"},"AuditLogEntry":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"record_id":{"type":"string","format":"uuid","title":"Record Id"},"action":{"type":"string","title":"Action"},"contributed_by_user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contributed By User Id"},"contributed_by_user_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contributed By User Name"},"contributed_by_role_at_time":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contributed By Role At Time"},"entry_metadata":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Entry Metadata"},"contributed_at":{"type":"string","format":"date-time","title":"Contributed At"}},"type":"object","required":["id","record_id","action","contributed_by_user_id","contributed_by_user_name","contributed_by_role_at_time","contributed_at"],"title":"AuditLogEntry","description":"One cb_record_provenance row: who did what to a record, and when."},"AuditLogResponse":{"properties":{"entries":{"items":{"$ref":"#/components/schemas/AuditLogEntry"},"type":"array","title":"Entries"},"total":{"type":"integer","title":"Total","default":0},"limit":{"type":"integer","title":"Limit"},"offset":{"type":"integer","title":"Offset"}},"type":"object","required":["entries","limit","offset"],"title":"AuditLogResponse","description":"Response for an object's audit log (GET /objects/{slug}/audit)."},"AuthoredKnowledgeRequest":{"properties":{"concept_type":{"type":"string","maxLength":100,"minLength":1,"title":"Concept Type"},"title":{"type":"string","maxLength":500,"minLength":1,"title":"Title"},"body":{"type":"string","maxLength":2000000,"title":"Body"},"visibility":{"type":"string","maxLength":32,"title":"Visibility","default":"organization"},"owner_id":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Owner Id"},"review_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Review At"},"stale_after":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Stale After"},"sources":{"items":{"$ref":"#/components/schemas/SourceInput"},"type":"array","maxItems":50,"title":"Sources"}},"type":"object","required":["concept_type","title","body"],"title":"AuthoredKnowledgeRequest","description":"Write a knowledge concept by hand. Spends nothing.\n\nThis is the GOVERNED write path: the entry lands as a draft and moves\nthrough the review queue at `GET /knowledge/governance`. It does not\nproject into the brain until it is approved there."},"AutoMergeRequest":{"properties":{"entity_type":{"type":"string","enum":["contact","company"],"title":"Entity Type","description":"Object to merge."},"dry_run":{"type":"boolean","title":"Dry Run","description":"Report what would merge without merging it.","default":false}},"type":"object","required":["entity_type"],"title":"AutoMergeRequest","description":"Run auto-merge once. NOT REVERSIBLE unless you undo each merge.\n\nHonours the org's own auto-merge and shadow-mode settings: with either\ndisabled the response SAYS SO instead of failing, so a 200 does not by\nitself mean records were merged. Send `dry_run=true` first."},"AutoSeedProposalsRequest":{"properties":{"signal_type":{"type":"string","enum":["jobs","job_changes"],"title":"Signal Type","description":"`jobs` (Hiring Wave) or `job_changes` (Talent Moves).","default":"jobs"}},"type":"object","title":"AutoSeedProposalsRequest","description":"Propose hiring keywords from the org's own context."},"AutoWarmupRequest":{"properties":{"enabled":{"type":"boolean","title":"Enabled","description":"True enrols new mailboxes automatically and bills warmup for them"}},"type":"object","required":["enabled"],"title":"AutoWarmupRequest","description":"Turn automatic warmup enrolment on or off for this domain.\n\nON means every mailbox bought on this domain is enrolled in warmup\nautomatically, which is a RECURRING credit charge per mailbox."},"AutopilotPreferencesRequest":{"properties":{"mode":{"type":"string","enum":["approval","auto"],"title":"Mode","description":"'approval' queues every retirement for a human; 'auto' lets the autopilot act and SPEND"},"max_auto_retirements_per_month":{"type":"integer","maximum":100.0,"minimum":0.0,"title":"Max Auto Retirements Per Month","description":"Ceiling on automatic retirements per calendar month"},"monthly_spend_ceiling_credits":{"type":"integer","maximum":500000.0,"minimum":0.0,"title":"Monthly Spend Ceiling Credits","description":"Ceiling on credits the autopilot may spend per calendar month"}},"type":"object","required":["mode","max_auto_retirements_per_month","monthly_spend_ceiling_credits"],"title":"AutopilotPreferencesRequest","description":"Replace the org's deliverability-autopilot preferences.\n\n``mode='auto'`` authorises the autopilot to retire and REPLACE failing\nmailboxes without asking, up to ``monthly_spend_ceiling_credits`` of the\norg's credits each month. That is why this is not an ordinary write."},"AvailabilityInput":{"properties":{"days":{"items":{"type":"integer"},"type":"array","title":"Days"},"start_time":{"type":"string","title":"Start Time"},"end_time":{"type":"string","title":"End Time"}},"type":"object","required":["days","start_time","end_time"],"title":"AvailabilityInput"},"AvailabilityInterval":{"properties":{"start":{"type":"string","maxLength":5,"minLength":5,"pattern":"^([01]\\d|2[0-3]):[0-5]\\d$","title":"Start"},"end":{"type":"string","maxLength":5,"minLength":5,"pattern":"^(([01]\\d|2[0-3]):[0-5]\\d|24:00)$","title":"End"},"day":{"type":"integer","maximum":6.0,"minimum":0.0,"title":"Day"}},"type":"object","required":["start","end","day"],"title":"AvailabilityInterval","description":"A weekly recurring window. `day` is 0-6 with Monday = 0."},"AvailabilityOverride":{"properties":{"date":{"type":"string","maxLength":10,"minLength":10,"pattern":"^\\d{4}-\\d{2}-\\d{2}$","title":"Date"},"intervals":{"items":{"$ref":"#/components/schemas/AvailabilityWindow"},"type":"array","maxItems":10,"title":"Intervals"}},"type":"object","required":["date"],"title":"AvailabilityOverride","description":"A single calendar date whose windows REPLACE that weekday's windows.\n\nAn empty `intervals` list means closed all day — that is the whole point of an\noverride, so it is not treated as \"unset\". Window `day` values are ignored\nhere (the date already fixes the day), and a client that sends one has it\ndropped by Pydantic's default `extra=\"ignore\"`."},"AvailabilityWindow":{"properties":{"start":{"type":"string","maxLength":5,"minLength":5,"pattern":"^([01]\\d|2[0-3]):[0-5]\\d$","title":"Start"},"end":{"type":"string","maxLength":5,"minLength":5,"pattern":"^(([01]\\d|2[0-3]):[0-5]\\d|24:00)$","title":"End"}},"type":"object","required":["start","end"],"title":"AvailabilityWindow","description":"One open window inside a single day, as wall-clock `HH:MM`.\n\n`end <= start` means the window crosses midnight into the next day; `\"24:00\"`\nis a legal `end` only and means end-of-day.\n\nBoth fields pin an exact LENGTH as well as a pattern, because a container's\n`max_length` bounds the element COUNT and never a nested string — the bound on\nthe string itself has to live here.\n\nThe length pin is redundant against today's engine and kept anyway: pydantic\ncompiles this pattern with the Rust regex crate, whose `$` matches only at the\nend of the haystack, so \"09:00\\n\" is already rejected. Python's `re`, which\npydantic falls back to for patterns the Rust engine cannot compile, matches `$`\nBEFORE a trailing newline and would let it through. Five characters cannot hold\na newline either way, so the pin makes the guarantee engine-independent."},"BackfillCaseStudiesRequest":{"properties":{"force":{"type":"boolean","title":"Force","description":"Re-extract documents already processed.","default":false}},"type":"object","title":"BackfillCaseStudiesRequest","description":"Extract structured metadata from case-study documents. SPENDS CREDIT."},"BackupDownloadResponse":{"properties":{"url":{"type":"string","title":"Url"},"expires_at":{"type":"string","format":"date-time","title":"Expires At"},"filename":{"type":"string","title":"Filename"},"archive_bytes":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Archive Bytes"},"archive_sha256":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Archive Sha256"},"format_version":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Format Version"}},"type":"object","required":["url","expires_at","filename"],"title":"BackupDownloadResponse","description":"A link to the archive (NDJSON, ``application/x-ndjson``) valid until ``expires_at`` (a few minutes)."},"BackupJobListResponse":{"properties":{"backups":{"items":{"$ref":"#/components/schemas/BackupJobResponse"},"type":"array","title":"Backups"},"total":{"type":"integer","title":"Total"},"limit":{"type":"integer","title":"Limit"},"offset":{"type":"integer","title":"Offset"},"storage_configured":{"type":"boolean","title":"Storage Configured","description":"False while backup storage is not configured: starting a backup would answer 503.","default":true}},"type":"object","required":["backups","total","limit","offset"],"title":"BackupJobListResponse"},"BackupJobResponse":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"status":{"type":"string","enum":["pending","running","completed","failed","expired"],"title":"Status"},"scope":{"anyOf":[{"type":"string","enum":["complete","restricted"]},{"type":"null"}],"title":"Scope"},"format_version":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Format Version"},"archive_bytes":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Archive Bytes"},"archive_sha256":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Archive Sha256"},"counts":{"additionalProperties":{"type":"integer"},"type":"object","title":"Counts","description":"Rows per archive section."},"error_code":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Error Code"},"requested_by":{"$ref":"#/components/schemas/BackupRequester"},"created_at":{"type":"string","format":"date-time","title":"Created At"},"started_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Started At"},"completed_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Completed At"},"expires_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Expires At"},"download_available":{"type":"boolean","title":"Download Available","default":false},"restorable":{"type":"boolean","title":"Restorable","description":"Only a complete backup can be restored.","default":false},"not_restorable_reason":{"anyOf":[{"type":"string","enum":["restricted_backup","expired","not_completed"]},{"type":"null"}],"title":"Not Restorable Reason","description":"``restricted_backup``: made with restricted access, so it cannot be restored."},"history":{"anyOf":[{"type":"string","enum":["included","omitted"]},{"type":"null"}],"title":"History","description":"Whether the archive holds record history (who changed what). Null until the backup has run (and for a backup made before this was recorded)."},"history_reason":{"anyOf":[{"type":"string","enum":["audit_permission_required","audit_log_switched_off"]},{"type":"null"}],"title":"History Reason","description":"Why history was left out: ``audit_permission_required`` (the requester lacks objects:audit) or ``audit_log_switched_off`` (the audit log is off for this workspace). Null when included or unknown."}},"type":"object","required":["id","status","requested_by","created_at"],"title":"BackupJobResponse","description":"A workspace backup: ``complete`` (made by a workspace administrator: every object, field, grant and report) or\n``restricted`` (exactly what the requester could read). The archive is deleted 14 days after ``created_at``."},"BackupRequester":{"properties":{"is_you":{"type":"boolean","title":"Is You"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"kind":{"anyOf":[{"type":"string","enum":["member","api_key"]},{"type":"null"}],"title":"Kind"}},"type":"object","required":["is_you"],"title":"BackupRequester","description":"Who asked. ``name`` and ``kind`` are shown to a workspace administrator only (anyone else lists only their own\njobs and reads ``is_you``); ``name`` is the member's display name, None for an API key or an unknown member."},"BankDetailsRequest":{"properties":{"currency":{"type":"string","maxLength":3,"minLength":3,"title":"Currency"},"account_type":{"type":"string","minLength":1,"title":"Account Type","description":"From the `bank-requirements` response."},"details":{"additionalProperties":true,"type":"object","title":"Details","description":"Exactly the fields `bank-requirements` asked for."},"account_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Id","description":"Payout method id. Omit for your primary."}},"type":"object","required":["currency","account_type","details"],"title":"BankDetailsRequest","description":"Create the Wise recipient money is actually paid into.\n\n`details` is passed to Wise as-is and its required keys come from\n`GET /marketplace/me/payout-account/bank-requirements` for the SAME\ncurrency - they differ per currency and per account type, which is why this\nis an open dict rather than a fixed schema. Dotted keys (`address.country`)\nare nested server-side before the call.\n\n`account_id` targets one of several payout methods; omit it for the primary."},"BatchAssertResponse":{"properties":{"total":{"type":"integer","title":"Total"},"created":{"type":"integer","title":"Created","default":0},"updated":{"type":"integer","title":"Updated","default":0},"errors":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Errors","default":[]},"custom_fields":{"$ref":"#/components/schemas/CustomFieldWriteReport"},"warnings":{"items":{"type":"string"},"type":"array","title":"Warnings","description":"Advisory notes about values saved as sent that look wrong (e.g. an unrecognised seniority or country), prefixed with the row index. Empty when the input is clean."}},"type":"object","required":["total"],"title":"BatchAssertResponse"},"BatchCompanyAssertRequest":{"properties":{"list_id":{"type":"integer","title":"List Id","description":"Target list ID"},"companies":{"items":{"additionalProperties":true,"type":"object"},"type":"array","maxItems":100,"title":"Companies","description":"Up to 100 companies with domain or linkedin_url"},"create_missing_fields":{"type":"boolean","title":"Create Missing Fields","description":"When true, any key in `custom_fields` that matches no existing column is created as a NEW list-scoped custom column (max 100 per request) and then written. Default false preserves the previous behaviour of not creating columns implicitly.","default":false}},"type":"object","required":["list_id","companies"],"title":"BatchCompanyAssertRequest"},"BatchContactAssertRequest":{"properties":{"list_id":{"type":"integer","title":"List Id","description":"Target list ID"},"contacts":{"items":{"additionalProperties":true,"type":"object"},"type":"array","maxItems":100,"title":"Contacts","description":"Up to 100 contacts with work_email or linkedin_url"},"create_missing_fields":{"type":"boolean","title":"Create Missing Fields","description":"When true, any key in `custom_fields` that matches no existing column is created as a NEW list-scoped custom column (max 100 per request) and then written. Default false preserves the previous behaviour of not creating columns implicitly.","default":false}},"type":"object","required":["list_id","contacts"],"title":"BatchContactAssertRequest"},"BatchContactRequest":{"properties":{"email":{"type":"string","title":"Email"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"company_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Id"},"company_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Name"},"user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Id"},"address":{"anyOf":[{"$ref":"#/components/schemas/CrmAddress"},{"type":"null"}]},"custom_fields":{"items":{"$ref":"#/components/schemas/CrmCustomField"},"type":"array","title":"Custom Fields"},"crm_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Crm Id","description":"The record's id in the CRM. Required on update, ignored on create."}},"type":"object","required":["email"],"title":"BatchContactRequest","description":"One contact in a batch. `crm_id` is only read on the UPDATE path."},"BatchContactsRequest":{"properties":{"contacts":{"items":{"$ref":"#/components/schemas/BatchContactRequest"},"type":"array","minItems":1,"title":"Contacts"}},"type":"object","required":["contacts"],"title":"BatchContactsRequest","description":"A batch of contacts to create or update in one provider round trip."},"BatchEmailItem":{"properties":{"type":{"type":"string","enum":["compose","respond"],"title":"Type","description":"compose a new email, or respond to one."},"recipient_info":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Recipient Info","description":"compose: who it is to."},"email_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email Type","description":"compose: the register.","default":"professional"},"email_to_respond_subject":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email To Respond Subject","description":"respond: the subject being answered."},"email_to_respond_body":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email To Respond Body","description":"respond: the body being answered."},"sender_info":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sender Info","description":"respond: who sent it."},"thread_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Thread Id","description":"respond: the thread id."},"thread_emails":{"anyOf":[{"items":{"$ref":"#/components/schemas/EmailThreadMessage"},"type":"array"},{"type":"null"}],"title":"Thread Emails","description":"respond: earlier messages."},"response_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Response Type","description":"respond: the register.","default":"professional"},"context":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Context","description":"Instructions for either kind."}},"type":"object","required":["type"],"title":"BatchEmailItem","description":"voice `BatchEmailRequest`: one compose or respond job inside a batch."},"BatchEmailProcessing":{"properties":{"agent_id":{"type":"string","minLength":1,"title":"Agent Id"},"contact_id":{"type":"string","minLength":1,"title":"Contact Id"},"emails":{"items":{"$ref":"#/components/schemas/BatchEmailItem"},"type":"array","maxItems":50,"minItems":1,"title":"Emails"},"provider":{"type":"string","enum":["openai","anthropic","openrouter"],"title":"Provider","description":"LLM provider.","default":"openai"},"model":{"type":"string","title":"Model","description":"openai: gpt-4o or gpt-4o-mini. anthropic: claude-sonnet-4-6, claude-haiku-4-5-20251001 or claude-opus-4-6. Voice rejects any other pairing with a 422.","default":"gpt-4o"}},"type":"object","required":["agent_id","contact_id","emails"],"title":"BatchEmailProcessing","description":"voice `BatchEmailProcessingRequest`, without `org_id` / `agent_settings`."},"BatchFieldItem":{"properties":{"title":{"type":"string","title":"Title","description":"Column title, e.g. 'Job Level'"},"data_type":{"type":"string","title":"Data Type","description":"Column data type: 'text', 'int' (whole number), 'numeric' (decimal) or 'boolean' (yes/no). Unknown values 400.","default":"text"},"enrichment":{"anyOf":[{"$ref":"#/components/schemas/CreateFieldEnrichmentInput"},{"type":"null"}],"description":"Optional per-column waterfall enrichment block (identical shape to POST /fields). When supplied, a companion enrichment_configs row is created for that column so it's immediately runnable."}},"type":"object","required":["title"],"title":"BatchFieldItem","description":"One column in a batch-create request.\n\n`title`, `data_type` and the optional `enrichment` block are per-column;\n`list_id` and `entity` are shared at the parent `CreateFieldsBatchRequest`\nlevel (a batch targets one entity and, when enrichment is used, one list)."},"BatchFieldResult":{"properties":{"title":{"type":"string","title":"Title"},"id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"ok":{"type":"boolean","title":"Ok","default":true},"error":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Error","description":"Set when the column was created but its companion enrichment config failed."},"enrichment":{"anyOf":[{"$ref":"#/components/schemas/CreateFieldEnrichmentResponse"},{"type":"null"}]},"is_global":{"type":"boolean","title":"Is Global","description":"True when this column was created org-GLOBAL (no list_id was supplied) and will therefore appear on EVERY list in the org. Pass `list_id` to scope columns to one list.","default":false},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id","description":"The list this column is scoped to, or null when it is org-global."},"already_existed":{"type":"boolean","title":"Already Existed","description":"True when this column already existed (same name, same scope), so the existing column was returned instead of a new one.","default":false},"existing_data_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Existing Data Type","description":"When `already_existed` is true: the existing column's data type."},"warnings":{"items":{"type":"string"},"type":"array","title":"Warnings","description":"Non-blocking notices for this column (e.g. same name exists org-wide)."}},"type":"object","required":["title"],"title":"BatchFieldResult","description":"Per-column outcome inside a batch response."},"BatchGetByEmailRequest":{"properties":{"emails":{"items":{"type":"string"},"type":"array","minItems":1,"title":"Emails"}},"type":"object","required":["emails"],"title":"BatchGetByEmailRequest","description":"Look up existing CRM contacts by email. Reads; writes nothing."},"BatchQuoteActionRequest":{"properties":{"action":{"type":"string","enum":["archive","expire","revoke"],"title":"Action","description":"What to do to every quote in the list."},"quote_ids":{"items":{"type":"string"},"type":"array","maxItems":200,"minItems":1,"title":"Quote Ids","description":"Quote ids. An out-of-scope or unknown id is reported per-row, not fatal."}},"type":"object","required":["action","quote_ids"],"title":"BatchQuoteActionRequest","description":"Archive, expire or revoke up to 200 quotes.\n\nEach quote runs in its OWN transaction and reports its own outcome, so one\nbad row does not roll back the rest. The per-row result is the whole point\nof the endpoint - read it rather than the HTTP status."},"BillingListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"BillingListPayload","description":"An open envelope for a LIST result. The rows are always under `items`;\n`total` and paging fields ride along when the app reports them."},"BillingPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"BillingPayload","description":"An open envelope for one billing result."},"Block":{"properties":{"id":{"type":"string","pattern":"^[a-zA-Z0-9_-]{1,64}$","title":"Id"},"kind":{"type":"string","enum":["identity","contact","photo","logo","social","cta","banner","divider","disclaimer","green_footer","custom_html"],"title":"Kind"},"text":{"type":"string","maxLength":10000,"title":"Text","default":""},"url":{"type":"string","maxLength":2048,"title":"Url","default":""},"image":{"type":"string","maxLength":2048,"title":"Image","default":""},"locked":{"type":"boolean","title":"Locked","default":false},"required":{"type":"boolean","title":"Required","default":false}},"additionalProperties":false,"type":"object","required":["id","kind"],"title":"Block"},"BlockedSenderCreateRequest":{"properties":{"mailbox":{"type":"string","title":"Mailbox","description":"The mailbox to block them on."},"sender_email":{"type":"string","title":"Sender Email","description":"The address to block."},"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason"}},"type":"object","required":["mailbox","sender_email"],"title":"BlockedSenderCreateRequest","description":"Stop a sender reaching one mailbox.\n\nScoped to the MAILBOX, not the organisation: blocking on one mailbox does\nnot block the same sender on another."},"BlocklistCheckRequest":{"properties":{"domains":{"items":{"type":"string"},"type":"array","maxItems":50,"minItems":1,"title":"Domains","description":"Up to 50 domains or hostnames."}},"type":"object","required":["domains"],"title":"BlocklistCheckRequest"},"BlocklistRemovalCreateRequest":{"properties":{"domain_id":{"type":"integer","minimum":1.0,"title":"Domain Id","description":"The listed sending domain."},"ticket_ref":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Ticket Ref","description":"Your reference for the removal ticket."}},"type":"object","required":["domain_id"],"title":"BlocklistRemovalCreateRequest"},"BlocklistRemovalUpdateRequest":{"properties":{"ticket_ref":{"type":"string","maxLength":500,"minLength":1,"title":"Ticket Ref"}},"type":"object","required":["ticket_ref"],"title":"BlocklistRemovalUpdateRequest"},"BlogCreateRequest":{"properties":{"chat_bot_id":{"type":"string","title":"Chat Bot Id","description":"Owning chat bot id (UUID)."},"url":{"type":"string","maxLength":1000,"minLength":1,"title":"Url"},"title":{"type":"string","maxLength":500,"minLength":1,"title":"Title"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"image_url":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Image Url"},"paths":{"items":{"type":"string"},"type":"array","title":"Paths"},"surface":{"anyOf":[{"type":"string","enum":["external","internal"]},{"type":"null"}],"title":"Surface"},"active":{"type":"boolean","title":"Active","default":true},"display_order":{"type":"integer","maximum":9999.0,"minimum":0.0,"title":"Display Order","description":"Lower sorts first; ties break newest-first.","default":0}},"type":"object","required":["chat_bot_id","url","title"],"title":"BlogCreateRequest","description":"An article card in the widget's rail.\n\n`url` and `image_url` are validated by the app to be http/https; a scheme\nit refuses is a 422 here rather than a broken card later."},"BlogMetadataRequest":{"properties":{"url":{"type":"string","maxLength":1000,"minLength":1,"title":"Url","description":"Page to read og:title / og:description / og:image from."}},"type":"object","required":["url"],"title":"BlogMetadataRequest","description":"A URL to read Open Graph metadata from.\n\nPersists NOTHING. It fetches the page and returns its `og:title`,\n`og:description` and `og:image` so a caller can pre-fill an article card\ninstead of typing it - which is why it is tiered a read despite the verb."},"BlogUpdateRequest":{"properties":{"chat_bot_id":{"type":"string","title":"Chat Bot Id","description":"Owning chat bot id (UUID)."},"url":{"anyOf":[{"type":"string","maxLength":1000,"minLength":1},{"type":"null"}],"title":"Url"},"title":{"anyOf":[{"type":"string","maxLength":500,"minLength":1},{"type":"null"}],"title":"Title"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"image_url":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Image Url"},"paths":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Paths"},"surface":{"anyOf":[{"type":"string","enum":["external","internal"]},{"type":"null"}],"title":"Surface"},"active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Active"},"display_order":{"anyOf":[{"type":"integer","maximum":9999.0,"minimum":0.0},{"type":"null"}],"title":"Display Order"},"expected_revision":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Expected Revision"}},"type":"object","required":["chat_bot_id"],"title":"BlogUpdateRequest","description":"Partial edit of an article card. `chat_bot_id` locates the row."},"Body_add_mailbox_to_workspace_inbox_workspaces__workspace_id__mailboxes_post":{"properties":{"mailbox_id":{"type":"integer","title":"Mailbox Id","description":"Integer `mailboxes.id` - the database primary key, NOT the cron-job string id. The app is explicit about the difference and so is this."}},"type":"object","required":["mailbox_id"],"title":"Body_add_mailbox_to_workspace_inbox_workspaces__workspace_id__mailboxes_post"},"Body_attach_skill_collections_skills__action_id__collections_post":{"properties":{"collection_ids":{"items":{"type":"integer"},"type":"array","minItems":1,"title":"Collection Ids","description":"Collections to attach. Additive - existing links survive."}},"type":"object","required":["collection_ids"],"title":"Body_attach_skill_collections_skills__action_id__collections_post"},"Body_attach_skills_to_agent_voice_agents__agent_id__skills_post":{"properties":{"action_ids":{"items":{},"type":"array","minItems":1,"title":"Action Ids","description":"Skill `action_id`s. Additive - existing skills are kept."}},"type":"object","required":["action_ids"],"title":"Body_attach_skills_to_agent_voice_agents__agent_id__skills_post"},"Body_clone_agent_voice_agents_clone_post":{"properties":{"source_agent_id":{"type":"string","title":"Source Agent Id","description":"Agent or template to copy."},"new_agent_name":{"type":"string","title":"New Agent Name","description":"Name for the copy."},"new_agent_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"New Agent Id","description":"Id for the copy. Generated when omitted."},"role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Role","description":"Override the role."},"entity_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Type","description":"Override: \"agent\" or \"twin\"."},"overrides":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Overrides","description":"Field overrides applied to the copy."}},"type":"object","required":["source_agent_id","new_agent_name"],"title":"Body_clone_agent_voice_agents_clone_post"},"Body_clone_voice_voice_voice_library_voices_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"A `.wav` or `.mp3` sample of at most ten seconds. 25 MB maximum."}},"type":"object","required":["file"],"title":"Body_clone_voice_voice_voice_library_voices_post"},"Body_connect_conferencing_appointments_conferencing_connect__provider__post":{"properties":{"link":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Link"}},"type":"object","title":"Body_connect_conferencing_appointments_conferencing_connect__provider__post"},"Body_create_bug_report_bug_reports_post":{"properties":{"title":{"type":"string","maxLength":255,"minLength":1,"title":"Title"},"description":{"type":"string","minLength":10,"title":"Description"},"severity":{"type":"string","enum":["low","medium","high","critical"],"title":"Severity","default":"medium"},"steps_to_reproduce":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Steps To Reproduce"},"page_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Page Url"},"session_replay_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Replay Id"},"product_slug":{"anyOf":[{"type":"string","pattern":"^[a-z][a-z0-9-]{0,32}$"},{"type":"null"}],"title":"Product Slug"},"screenshots":{"items":{"type":"string","format":"binary"},"type":"array","title":"Screenshots","description":"Images, at most three.","default":[]}},"type":"object","required":["title","description"],"title":"Body_create_bug_report_bug_reports_post"},"Body_create_skill_test_case_skills__action_id__test_cases_post":{"properties":{"name":{"type":"string","maxLength":200,"minLength":1,"title":"Name","description":"Human label."},"input_data":{"additionalProperties":true,"type":"object","title":"Input Data","description":"The fixture, same shape as an execution's input."},"expected_output":{"anyOf":[{},{"type":"null"}],"title":"Expected Output","description":"What the assertion compares against."},"assertion_type":{"type":"string","title":"Assertion Type","description":"\"exact\", \"contains\" or \"llm_judge\". `llm_judge` is skipped by dry runs.","default":"contains"},"assertion_config":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Assertion Config","description":"Extra configuration for the assertion."}},"type":"object","required":["name","input_data"],"title":"Body_create_skill_test_case_skills__action_id__test_cases_post"},"Body_create_twin_voice_twins_post":{"properties":{"agent_id":{"type":"string","minLength":1,"title":"Agent Id","description":"The id the new twin takes; 409 if it exists."},"name":{"type":"string","title":"Name"},"role":{"type":"string","title":"Role"},"description":{"type":"string","title":"Description"},"tone":{"type":"number","maximum":1.0,"minimum":0.0,"title":"Tone"},"conciseness":{"type":"number","maximum":1.0,"minimum":0.0,"title":"Conciseness"},"assertiveness":{"type":"number","maximum":1.0,"minimum":0.0,"title":"Assertiveness"},"persona":{"type":"string","title":"Persona"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone"},"voice":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Voice"},"calendar":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Calendar"},"avatar_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Avatar Url"},"use_company_knowledge":{"type":"boolean","title":"Use Company Knowledge","default":true},"collections":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Collections","description":"JSON array of collection ids, as a string."},"background":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Background"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url"},"linkedin_data":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Data","description":"JSON, as a string, e.g. from `twins/extract-linkedin`."},"outbound_voicemail_prompt":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Outbound Voicemail Prompt"},"company_name_pronunciation":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Name Pronunciation"},"created_by_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created By Email","description":"The person the twin is modelled on."},"writing_style_file":{"anyOf":[{"type":"string","format":"binary"},{"type":"null"}],"title":"Writing Style File","description":"A writing sample. 25 MB maximum."}},"type":"object","required":["agent_id","name","role","description","tone","conciseness","assertiveness","persona"],"title":"Body_create_twin_voice_twins_post"},"Body_decline_inbound_call_voice_inbound_calls_decline_post":{"properties":{"room_name":{"type":"string","title":"Room Name","description":"The ringing call's room name."},"action":{"type":"string","title":"Action","description":"\"hangup\" ends the call. Voice treats anything else as a decline.","default":"hangup"}},"type":"object","required":["room_name"],"title":"Body_decline_inbound_call_voice_inbound_calls_decline_post"},"Body_infer_skill_variable_skills_infer_variable_post":{"properties":{"entity_data":{"additionalProperties":true,"type":"object","title":"Entity Data","description":"The contact or company record, same shape as an execution input."},"entity_data_type":{"type":"string","title":"Entity Data Type","description":"\"contact\" or \"company\"."},"entity_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Id","description":"Record id. Used for cache keying only."}},"type":"object","required":["entity_data","entity_data_type"],"title":"Body_infer_skill_variable_skills_infer_variable_post"},"Body_parse_script_parameters_skills_parse_script_parameters_post":{"properties":{"code":{"type":"string","title":"Code","description":"The script source."},"language":{"type":"string","title":"Language","description":"\"python\", \"javascript\" or \"typescript\".","default":"python"}},"type":"object","required":["code"],"title":"Body_parse_script_parameters_skills_parse_script_parameters_post"},"Body_post_desk_voice_memo_desk_voice_memo_post":{"properties":{"audio":{"type":"string","format":"binary","title":"Audio","description":"The recorded memo, any Whisper-supported format. 5 MB maximum."},"deal_id":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Deal Id","description":"Deal the memo is about, if any."}},"type":"object","required":["audio"],"title":"Body_post_desk_voice_memo_desk_voice_memo_post"},"Body_rename_chat_agent_conversation_voice_chat_agent_conversations__chat_id__name_put":{"properties":{"name":{"type":"string","minLength":1,"title":"Name","description":"The new name."}},"type":"object","required":["name"],"title":"Body_rename_chat_agent_conversation_voice_chat_agent_conversations__chat_id__name_put"},"Body_request_execution_changes_workflows_executions_request_changes_post":{"properties":{"workflow_id":{"type":"string","title":"Workflow Id","description":"The workflow the run belongs to."},"requested_by":{"type":"string","title":"Requested By","description":"Who is asking for changes."},"feedback":{"type":"string","maxLength":2000,"minLength":1,"title":"Feedback","description":"REQUIRED and non-blank. It is the value the revise branch reads as `${<human_node>.feedback}` - an empty one sends the workflow down the revise path with nothing to revise against."}},"type":"object","required":["workflow_id","requested_by","feedback"],"title":"Body_request_execution_changes_workflows_executions_request_changes_post"},"Body_research_company_voice_research_company_post":{"properties":{"company_name":{"type":"string","title":"Company Name","description":"Company to research."},"company_url":{"type":"string","title":"Company Url","description":"Company website."},"research_depth":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Research Depth","description":"How far to go. Deeper costs more."},"specific_areas":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Specific Areas","description":"Narrow the research to these areas."},"include_scraping":{"type":"boolean","title":"Include Scraping","description":"False skips fetching the company's own site.","default":true},"max_sources":{"type":"integer","maximum":50.0,"minimum":1.0,"title":"Max Sources","description":"Ceiling on sources checked. Cost scales with it.","default":10}},"type":"object","required":["company_name","company_url"],"title":"Body_research_company_voice_research_company_post"},"Body_research_org_chart_voice_research_org_chart_post":{"properties":{"company_name":{"type":"string","title":"Company Name","description":"Company to research."},"company_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Url","description":"Company website."},"domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain","description":"Company domain, e.g. `graph8.com`."},"research_depth":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Research Depth","description":"\"basic\", \"standard\" or \"deep\". Deeper costs more."},"include_contact_info":{"type":"boolean","title":"Include Contact Info","description":"False omits emails and phone numbers, which is the expensive part.","default":true}},"type":"object","required":["company_name"],"title":"Body_research_org_chart_voice_research_org_chart_post"},"Body_save_workflow_integration_workflows_integrations__provider_name__post":{"properties":{"api_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Api Key","description":"The provider credential. WRITE-ONLY: no route on this API returns it. Omitting it on an update leaves the stored key in place."},"configuration":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Configuration","description":"Provider-specific settings."}},"type":"object","title":"Body_save_workflow_integration_workflows_integrations__provider_name__post"},"Body_set_onboarding_voice_voice_voice_library_onboarding_voice_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"A `.wav` or `.mp3` sample. 25 MB maximum."}},"type":"object","required":["file"],"title":"Body_set_onboarding_voice_voice_voice_library_onboarding_voice_post"},"Body_set_provider_link_appointments_conferencing__provider__link_put":{"properties":{"link":{"type":"string","title":"Link"}},"type":"object","required":["link"],"title":"Body_set_provider_link_appointments_conferencing__provider__link_put"},"Body_store_campaign_memory_voice_campaigns_memory_post":{"properties":{"contact_id":{"type":"integer","title":"Contact Id","description":"The contact this happened with."},"content":{"type":"string","title":"Content","description":"What happened, in prose."}},"type":"object","required":["contact_id","content"],"title":"Body_store_campaign_memory_voice_campaigns_memory_post"},"Body_transcribe_call_flow_example_voice_call_flow_examples_transcribe_post":{"properties":{"audio_file":{"type":"string","format":"binary","title":"Audio File","description":"MP3, WAV, WebM, OGG or FLAC. 25 MB maximum."}},"type":"object","required":["audio_file"],"title":"Body_transcribe_call_flow_example_voice_call_flow_examples_transcribe_post"},"Body_update_agent_memory_voice_agents__agent_id__memory_post":{"properties":{"contact_id":{"type":"string","title":"Contact Id","description":"Who the conversation was with."},"interactions":{"items":{},"type":"array","title":"Interactions","description":"Ordered messages, each `{\"role\": \"user\"|\"assistant\", \"content\": \"...\"}`. Oldest first."},"session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Id","description":"Groups messages into one conversation. Generated when omitted."},"actor":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Actor","description":"Who the human side was."},"interaction_type":{"type":"string","title":"Interaction Type","description":"Channel: \"chat\", \"email\", \"phone_call\", ...","default":"chat"}},"type":"object","required":["contact_id","interactions"],"title":"Body_update_agent_memory_voice_agents__agent_id__memory_post"},"Body_update_twin_voice_twins__agent_id__put":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Role"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"tone":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Tone"},"conciseness":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Conciseness"},"assertiveness":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Assertiveness"},"persona":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Persona"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone"},"voice":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Voice"},"calendar":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Calendar"},"avatar_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Avatar Url"},"use_company_knowledge":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Use Company Knowledge"},"background":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Background"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url"},"linkedin_data":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Data","description":"JSON, as a string, e.g. from `twins/extract-linkedin`."},"inbound_instructions":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Inbound Instructions"},"outbound_instructions":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Outbound Instructions"},"outbound_voicemail_prompt":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Outbound Voicemail Prompt"},"company_name_pronunciation":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Name Pronunciation"},"writing_style_file":{"anyOf":[{"type":"string","format":"binary"},{"type":"null"}],"title":"Writing Style File","description":"A writing sample the twin imitates. 25 MB maximum."}},"type":"object","title":"Body_update_twin_voice_twins__agent_id__put"},"Body_upload_account_correspondence_accounts__account_id__correspondence_upload_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"A text or .eml file. Its text becomes the content."},"channel":{"type":"string","title":"Channel","description":"`email`, `linkedin` or `call_notes`."},"direction":{"type":"string","title":"Direction","description":"`inbound` or `outbound`.","default":"inbound"}},"type":"object","required":["file","channel"],"title":"Body_upload_account_correspondence_accounts__account_id__correspondence_upload_post"},"Body_upload_ad_image_ad_campaigns_images_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"JPEG, PNG, GIF or WebP, under 10 MB. Not SVG."}},"type":"object","required":["file"],"title":"Body_upload_ad_image_ad_campaigns_images_post"},"Body_upload_agency_rep_video_intro_marketplace_agencies__slug__reps__sdr_id__video_intro_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"The rep's intro video."}},"type":"object","required":["file"],"title":"Body_upload_agency_rep_video_intro_marketplace_agencies__slug__reps__sdr_id__video_intro_post"},"Body_upload_agency_resumes_marketplace_agencies__slug__intake_upload_post":{"properties":{"files":{"items":{"type":"string","format":"binary"},"type":"array","title":"Files","description":"Resume PDFs. 5 MB each."}},"type":"object","required":["files"],"title":"Body_upload_agency_resumes_marketplace_agencies__slug__intake_upload_post"},"Body_upload_agent_documents_voice_agents__agent_id__documents_upload_post":{"properties":{"files":{"items":{"type":"string","format":"binary"},"type":"array","title":"Files","description":"PDF, DOCX or text. 25 MB maximum each."}},"type":"object","required":["files"],"title":"Body_upload_agent_documents_voice_agents__agent_id__documents_upload_post"},"Body_upload_collection_file_voice_collections__collection_id__files_upload_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"The document. 25 MB maximum."},"folder_path":{"type":"string","title":"Folder Path","description":"Folder inside the collection. Empty is the root.","default":""}},"type":"object","required":["file"],"title":"Body_upload_collection_file_voice_collections__collection_id__files_upload_post"},"Body_upload_collection_files_voice_collections__collection_id__files_upload_multiple_post":{"properties":{"files":{"items":{"type":"string","format":"binary"},"type":"array","title":"Files","description":"The documents. 25 MB maximum each."},"folder_path":{"type":"string","title":"Folder Path","description":"Folder inside the collection. Empty is the root.","default":""}},"type":"object","required":["files"],"title":"Body_upload_collection_files_voice_collections__collection_id__files_upload_multiple_post"},"Body_upload_company_profile_logo_company_profile_logo_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"PNG, JPEG, WebP or SVG image."}},"type":"object","required":["file"],"title":"Body_upload_company_profile_logo_company_profile_logo_post"},"Body_upload_import_file_imports_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"CSV or Excel file. 25 MB maximum."}},"type":"object","required":["file"],"title":"Body_upload_import_file_imports_post"},"Body_upload_job_post_jd_marketplace_job_posts__post_id__jd_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"The job description PDF. 10 MB maximum."}},"type":"object","required":["file"],"title":"Body_upload_job_post_jd_marketplace_job_posts__post_id__jd_post"},"Body_upload_knowledge_base_file_voice_knowledge_base_files_upload_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"The document. 25 MB maximum."},"filename":{"type":"string","minLength":1,"title":"Filename","description":"Name to store it under."}},"type":"object","required":["file","filename"],"title":"Body_upload_knowledge_base_file_voice_knowledge_base_files_upload_post"},"Body_upload_library_document_library_documents_upload_post":{"properties":{"folder_path":{"type":"string","title":"Folder Path","description":"Where it lands. The folder must already exist."},"file":{"type":"string","format":"binary","title":"File","description":"The file. 50 MB maximum."},"context_type":{"type":"string","enum":["global","campaign","account"],"title":"Context Type","default":"global"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id","description":"REQUIRED when `context_type` is `campaign`."},"account_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Id","description":"REQUIRED when `context_type` is `account`."}},"type":"object","required":["folder_path","file"],"title":"Body_upload_library_document_library_documents_upload_post"},"Body_upload_library_documents_library_documents_upload_batch_post":{"properties":{"folder_path":{"type":"string","title":"Folder Path","description":"Where they all land. One folder for the batch."},"files":{"items":{"type":"string","format":"binary"},"type":"array","title":"Files","description":"The files. Each is subject to the same rules."},"context_type":{"type":"string","enum":["global","campaign","account"],"title":"Context Type","default":"global"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id","description":"REQUIRED when `context_type` is `campaign`."},"account_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Id","description":"REQUIRED when `context_type` is `account`."}},"type":"object","required":["folder_path","files"],"title":"Body_upload_library_documents_library_documents_upload_batch_post"},"Body_upload_my_headshot_marketplace_me_headshot_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"JPEG, PNG or WebP. 5 MB maximum."}},"type":"object","required":["file"],"title":"Body_upload_my_headshot_marketplace_me_headshot_post"},"Body_upload_my_resume_marketplace_me_resume_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"PDF. 5 MB maximum."}},"type":"object","required":["file"],"title":"Body_upload_my_resume_marketplace_me_resume_post"},"Body_upload_my_video_intro_marketplace_me_video_intro_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"MP4 or WebM. 50 MB maximum."}},"type":"object","required":["file"],"title":"Body_upload_my_video_intro_marketplace_me_video_intro_post"},"Body_upload_org_video_org_videos_upload_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"mp4, webm or quicktime; at most 100 MB."},"title":{"type":"string","title":"Title","default":""},"alt_text":{"type":"string","title":"Alt Text","default":""},"poster_url":{"type":"string","title":"Poster Url","default":""},"duration_seconds":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Duration Seconds"}},"type":"object","required":["file"],"title":"Body_upload_org_video_org_videos_upload_post"},"Body_upload_persona_photo_mailboxes_personas__persona_id__photo_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"Image file. Oversized or non-image uploads are refused with a 422."}},"type":"object","required":["file"],"title":"Body_upload_persona_photo_mailboxes_personas__persona_id__photo_post"},"Body_upload_profile_avatar_profile_avatar_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"JPEG, PNG or WebP, 5 MB at most."}},"type":"object","required":["file"],"title":"Body_upload_profile_avatar_profile_avatar_post"},"Body_upload_quote_document_quote_settings_documents_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"The PDF. 10 MB maximum; PDFs only."},"title":{"type":"string","title":"Title","description":"How the document is listed and attached."},"doc_type":{"type":"string","title":"Doc Type","description":"`nda`, `msa` or `other`. Anything else is COERCED to `other` by the app rather than rejected, so a typo lands the document in the library under the wrong type instead of failing loudly.","default":"other"}},"type":"object","required":["file","title"],"title":"Body_upload_quote_document_quote_settings_documents_post"},"Body_upload_quote_evidence_quotes__quote_id__evidence_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"A PDF, at most 10 MB."}},"type":"object","required":["file"],"title":"Body_upload_quote_evidence_quotes__quote_id__evidence_post"},"Body_upload_security_questionnaire_accounts__account_id__security_questionnaires_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"The buyer's questionnaire, XLSX or PDF."}},"type":"object","required":["file"],"title":"Body_upload_security_questionnaire_accounts__account_id__security_questionnaires_post"},"Body_upload_video_recording_voice_video_recordings_upload_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"MP4, MOV, AVI, FLV, MKV or WebM. 500 MB maximum."},"user_id":{"type":"string","minLength":1,"title":"User Id","description":"Whose recording this is, e.g. a candidate or employee id."},"folder_path":{"type":"string","title":"Folder Path","description":"Optional folder, e.g. `interviews/q4`.","default":""},"language":{"type":"string","title":"Language","description":"Transcription language.","default":"en"},"metadata_json":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Metadata Json","description":"Optional JSON metadata, as a string."}},"type":"object","required":["file","user_id"],"title":"Body_upload_video_recording_voice_video_recordings_upload_post"},"Body_upload_webchat_image_webchat_images_post":{"properties":{"file":{"type":"string","format":"binary","title":"File","description":"JPEG, PNG, GIF or WebP. 10 MB maximum."}},"type":"object","required":["file"],"title":"Body_upload_webchat_image_webchat_images_post"},"BookedMeeting":{"properties":{"id":{"type":"integer","title":"Id"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"start_time":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Start Time"},"end_time":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"End Time"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"organizer":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Organizer"},"attendees":{"type":"integer","title":"Attendees","description":"Attendee count","default":0}},"type":"object","required":["id"],"title":"BookedMeeting","description":"One booked calendar meeting (non-cancelled, non-private)."},"BookingEventTypePatchRequest":{"properties":{"selected_event_type_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Selected Event Type Id"}},"type":"object","title":"BookingEventTypePatchRequest","description":"Mirrors `BookingEventTypePatchRequest`."},"BrandExtractionRequest":{"properties":{"website_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Website Url","description":"Site to extract from. Omit to re-extract the org's current website."}},"type":"object","title":"BrandExtractionRequest","description":"Mirrors `campaign_builder.routers.brand_kit.TriggerExtractionPayload`.\n\n`website_url` omitted re-runs extraction against the website already on the\norg's company profile. Supplying one EXTRACTS A DIFFERENT SITE, which\nreplaces the org's design tokens and homepage capture."},"BrandReExtractRequest":{"properties":{"website_url":{"type":"string","maxLength":2048,"minLength":1,"title":"Website Url"}},"type":"object","required":["website_url"],"title":"BrandReExtractRequest","description":"Re-scrape the website and rebuild the Design system. `website_url` is required."},"BrowserExchangeRequest":{"properties":{"app_id":{"type":"string","title":"App Id","description":"Target app id (dapp_-prefixed)"},"scopes":{"items":{"type":"string"},"type":"array","title":"Scopes","description":"Scopes to embed in the token"}},"type":"object","required":["app_id"],"title":"BrowserExchangeRequest","description":"Body for the browser exchange — target app + non-identity params ONLY.\n\nIdentity is DERIVED SERVER-SIDE from the authenticated PropelAuth principal\n(locked decision §5: \"browser auth = PropelAuth login -> short-lived graph8\napp token\"): ``subject`` / ``client_org_id`` / ``role`` come from the\nvalidated principal, never from this body, so a client cannot self-assert who\nit is or escalate its role. Any ``subject`` / ``client_org_id`` / ``role``\nkeys a caller forges into the body are ignored (pydantic drops unknown fields)."},"BugReportCommentRequest":{"properties":{"body":{"type":"string","minLength":1,"title":"Body"}},"type":"object","required":["body"],"title":"BugReportCommentRequest"},"BugReportListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"BugReportListPayload","description":"Bug reports under `items`."},"BugReportPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"BugReportPayload","description":"A bug report with its status, comments and screenshots."},"BulkAssignMembersRequest":{"properties":{"include_future_joiners":{"type":"boolean","title":"Include Future Joiners","description":"When true, members who join the organisation LATER also get a copy automatically. A standing rule, not a one-off action.","default":false}},"type":"object","title":"BulkAssignMembersRequest","description":"Give every active member a copy of a managed template."},"BulkCompetitorItem":{"properties":{"domain":{"type":"string","maxLength":255,"minLength":1,"title":"Domain"},"name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Name"},"tier":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Tier"},"scan_config":{"anyOf":[{"$ref":"#/components/schemas/ScanConfigDTO"},{"type":"null"}]}},"type":"object","required":["domain"],"title":"BulkCompetitorItem"},"BulkCompetitorsRequest":{"properties":{"competitors":{"items":{"$ref":"#/components/schemas/BulkCompetitorItem"},"type":"array","maxItems":20,"title":"Competitors"},"scan_on_add":{"type":"boolean","title":"Scan On Add","default":false}},"type":"object","title":"BulkCompetitorsRequest"},"BulkCreateFromListRequest":{"properties":{"list_id":{"type":"integer","title":"List Id","description":"The graph8 audience to read profiles from."},"listener_type":{"type":"string","const":"user","title":"Listener Type","description":"Only `user` listeners can be bulk-created from a list.","default":"user"},"platform":{"type":"string","enum":["x","linkedin","reddit","instagram","youtube"],"title":"Platform","default":"x"},"platforms":{"anyOf":[{"items":{"type":"string","enum":["x","linkedin","reddit","instagram","youtube"]},"type":"array"},{"type":"null"}],"title":"Platforms","description":"Create one listener per platform. Overrides `platform`."}},"type":"object","required":["list_id"],"title":"BulkCreateFromListRequest","description":"Create one `user` listener per social profile on a graph8 list.\n\nNo platform lookup happens here - handles are resolved lazily by the\npolling worker, so this does not consume quota per row at creation time."},"BulkDealChange":{"properties":{"stage":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage"},"stage_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage Id"},"pipeline_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Pipeline Id"},"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id"},"amount":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Amount"},"currency":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Currency"},"close_date":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Close Date"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"next_step":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Next Step"},"custom_fields":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Custom Fields"}},"type":"object","title":"BulkDealChange","description":"The change applied to EVERY deal in the batch.\n\nPUT semantics, and the distinction matters: `null` leaves a value alone,\nan EMPTY STRING clears it. So omitting a field and sending `\"\"` are\ndifferent instructions, and the second one is destructive."},"BulkDealUpdateRequest":{"properties":{"deal_ids":{"items":{"type":"string"},"type":"array","maxItems":100,"minItems":1,"title":"Deal Ids"},"change":{"$ref":"#/components/schemas/BulkDealChange"}},"type":"object","required":["deal_ids","change"],"title":"BulkDealUpdateRequest","description":"Apply one change to up to 100 deals.\n\nEach deal is checked against the caller's deal scope individually; one the\ncaller cannot write is reported rather than aborting the batch."},"BulkExtractRequest":{"properties":{"extractions":{"items":{"$ref":"#/components/schemas/ExtractColumnRequest"},"type":"array","maxItems":50,"minItems":1,"title":"Extractions"}},"type":"object","required":["extractions"],"title":"BulkExtractRequest","description":"Up to 50 extractions in one call."},"BulkProductSettingsRequest":{"properties":{"stripe_product_ids":{"items":{"type":"string"},"type":"array","title":"Stripe Product Ids","description":"Stripe product ids to update."},"updates":{"$ref":"#/components/schemas/ProductSettingsUpdateRequest"}},"type":"object","required":["stripe_product_ids","updates"],"title":"BulkProductSettingsRequest"},"BulkReinstateResponse":{"properties":{"reinstated":{"items":{"type":"integer"},"type":"array","title":"Reinstated"},"skipped":{"items":{"$ref":"#/components/schemas/ReinstateSkip"},"type":"array","title":"Skipped"},"total_requested":{"type":"integer","title":"Total Requested"},"not_found":{"items":{"type":"integer"},"type":"array","title":"Not Found","description":"Requested contact ids that match no contact (for example a mistyped id). They also appear in `skipped`."}},"type":"object","required":["total_requested"],"title":"BulkReinstateResponse"},"BulkSuppressResponse":{"properties":{"suppressed":{"type":"integer","title":"Suppressed"},"total_requested":{"type":"integer","title":"Total Requested"},"channel":{"type":"string","title":"Channel"},"not_found":{"items":{"type":"integer"},"type":"array","title":"Not Found","description":"Requested contact ids that match no contact; nothing was written for them."}},"type":"object","required":["suppressed","total_requested","channel"],"title":"BulkSuppressResponse"},"BusinessHoursScheduleRequest":{"properties":{"phone_number":{"type":"string","minLength":1,"title":"Phone Number"},"timezone":{"type":"string","minLength":1,"title":"Timezone","description":"IANA name (e.g. `America/New_York`). Voice rejects anything pytz cannot load."},"business_hours":{"$ref":"#/components/schemas/BusinessHoursWindow"},"business_hours_target":{"$ref":"#/components/schemas/BusinessHoursTargetRef"},"after_hours_target":{"$ref":"#/components/schemas/BusinessHoursTargetRef"}},"type":"object","required":["phone_number","timezone","business_hours","business_hours_target","after_hours_target"],"title":"BusinessHoursScheduleRequest","description":"Create or REPLACE the business-hours / after-hours pair for a number.\n\nThis is a two-rule bulk setup, not an addition: calling it again replaces\nboth rules rather than adding more."},"BusinessHoursTargetRef":{"properties":{"target_type":{"type":"string","enum":["ai_agent","department","extension","voicemail"],"title":"Target Type"},"target_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Id"}},"type":"object","required":["target_type"],"title":"BusinessHoursTargetRef","description":"Where a call goes in one half of the schedule."},"BusinessHoursWindow":{"properties":{"days":{"items":{"type":"string","enum":["mon","tue","wed","thu","fri","sat","sun"]},"type":"array","minItems":1,"title":"Days"},"start_time":{"type":"string","pattern":"^\\d{2}:\\d{2}$","title":"Start Time","description":"24h HH:MM."},"end_time":{"type":"string","pattern":"^\\d{2}:\\d{2}$","title":"End Time","description":"24h HH:MM."}},"type":"object","required":["days","start_time","end_time"],"title":"BusinessHoursWindow","description":"The open hours themselves."},"ButtonCreateRequest":{"properties":{"chat_bot_id":{"type":"string","title":"Chat Bot Id","description":"Owning chat bot id (UUID)."},"label":{"type":"string","maxLength":255,"minLength":1,"title":"Label"},"action":{"type":"string","enum":["link","question","calendar"],"title":"Action"},"value":{"type":"string","maxLength":1000,"minLength":1,"title":"Value","description":"URL for `link`, question text for `question`, slug for `calendar`."},"icon":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Icon"},"category":{"type":"string","maxLength":100,"minLength":1,"title":"Category"},"paths":{"items":{"type":"string"},"type":"array","title":"Paths","description":"URL paths where the button appears."},"active":{"type":"boolean","title":"Active","default":true},"surface":{"anyOf":[{"type":"string","enum":["external","internal"]},{"type":"null"}],"title":"Surface","description":"NULL shows it on BOTH widgets."}},"type":"object","required":["chat_bot_id","label","action","value","category"],"title":"ButtonCreateRequest","description":"A quick-action button in the widget.\n\n`value` means something different per `action`: a URL for `link`, the\nquestion text for `question`, a calendar slug for `calendar`. Sending the\nwrong kind is accepted here and fails at the widget, so it is spelled out\nrather than left to be discovered."},"ButtonUpdateRequest":{"properties":{"chat_bot_id":{"type":"string","title":"Chat Bot Id","description":"Owning chat bot id (UUID)."},"label":{"anyOf":[{"type":"string","maxLength":255,"minLength":1},{"type":"null"}],"title":"Label"},"action":{"anyOf":[{"type":"string","enum":["link","question","calendar"]},{"type":"null"}],"title":"Action"},"value":{"anyOf":[{"type":"string","maxLength":1000,"minLength":1},{"type":"null"}],"title":"Value"},"icon":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Icon"},"category":{"anyOf":[{"type":"string","maxLength":100,"minLength":1},{"type":"null"}],"title":"Category"},"paths":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Paths"},"active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Active"},"surface":{"anyOf":[{"type":"string","enum":["external","internal"]},{"type":"null"}],"title":"Surface"},"expected_revision":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Expected Revision"}},"type":"object","required":["chat_bot_id"],"title":"ButtonUpdateRequest","description":"Partial edit of a button. `chat_bot_id` locates the row."},"BuyingJourneyInterviewRequest":{"properties":{"answers":{"additionalProperties":true,"type":"object","minProperties":1,"title":"Answers","description":"Structured interview answers about how this organisation sells. Injected as highest-priority grounding the next time the buying journey document is generated."}},"type":"object","required":["answers"],"title":"BuyingJourneyInterviewRequest","description":"The typed form of the untyped `dict` body the interview route takes.\n\nThe app reads `answers` and 400s when it is empty. Typed so that is a 422,\nand so the shape is discoverable."},"CRMImportRequest":{"properties":{"connection_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Connection Id","description":"Which CRM connection to read."},"provider_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Provider Type","description":"CRM provider key, e.g. 'hubspot'."},"filters":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Filters"},"limit":{"type":"integer","maximum":10000.0,"minimum":1.0,"title":"Limit","default":1000},"raw_source_column_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Raw Source Column Id"},"entity_type":{"anyOf":[{"type":"string","enum":["contact","company"]},{"type":"null"}],"title":"Entity Type"},"crm_provider":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Crm Provider","description":"Legacy alias of `provider_type`."},"object_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Object Type","description":"Legacy alias of `entity_type` (plural form)."}},"type":"object","title":"CRMImportRequest","description":"Pull records out of a connected CRM into a workbench table."},"CalendarInviteCreateRequest":{"properties":{"title":{"type":"string","maxLength":1000,"minLength":1,"title":"Title"},"start_at":{"type":"string","format":"date-time","title":"Start At","description":"Start time WITH a timezone offset."},"tz":{"type":"string","title":"Tz","description":"IANA timezone the event is shown in, e.g. `Europe/London`."},"duration_minutes":{"type":"integer","maximum":1440.0,"minimum":1.0,"title":"Duration Minutes","default":45},"meeting_link":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Meeting Link","description":"An http(s) URL."},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"}},"type":"object","required":["title","start_at","tz"],"title":"CalendarInviteCreateRequest"},"CalendarInvitePayload":{"properties":{},"additionalProperties":true,"type":"object","title":"CalendarInvitePayload","description":"A calendar invite, including the public `ics_url`."},"CalendarInviteUpdateRequest":{"properties":{"title":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Title"},"start_at":{"type":"string","format":"date-time","title":"Start At","description":"Start time WITH a timezone offset."},"tz":{"type":"string","title":"Tz"},"duration_minutes":{"type":"integer","maximum":1440.0,"minimum":1.0,"title":"Duration Minutes","default":45},"meeting_link":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Meeting Link"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"}},"type":"object","required":["start_at","tz"],"title":"CalendarInviteUpdateRequest"},"CallControlRequest":{"properties":{"session_id":{"type":"string","title":"Session Id"},"call_id":{"type":"string","title":"Call Id"}},"type":"object","required":["session_id","call_id"],"title":"CallControlRequest","description":"Mirrors `DialerCallControl`. Ends a call already in progress."},"CallDispositionRequest":{"properties":{"disposition":{"type":"string","title":"Disposition"},"notes":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Notes"},"sentiment":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sentiment"},"callback_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Callback At"}},"type":"object","required":["disposition"],"title":"CallDispositionRequest","description":"Mirrors `CallDispositionRequest`. Records the outcome of a finished call.\n\n`disposition` is left an open string on purpose: the vocabulary is\nsystem values PLUS the org's own custom dispositions, so closing it here\nwould refuse a value the customer defined. `GET /voice/dispositions`\nlists what this org accepts."},"CallGradingResponse":{"properties":{"room_name":{"type":"string","title":"Room Name"},"status":{"type":"string","title":"Status","description":"ready | pending","default":"ready"},"grading":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Grading"},"reviewed":{"type":"boolean","title":"Reviewed","default":false},"reviewed_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reviewed At"}},"type":"object","required":["room_name"],"title":"CallGradingResponse","description":"AI grading for a single dialer call.\n\nThe ``status`` field flips to ``\"pending\"`` when the upstream service\nreturns 204 (grading still being computed). In that case ``grading``\nwill be empty and ``reviewed`` will be ``False``. Callers can poll\nuntil ``status == \"ready\"``."},"CallResultSearchRequest":{"properties":{"disposition":{"anyOf":[{"type":"string","enum":["booked","positive","neutral","negative","voicemail"]},{"type":"null"}],"title":"Disposition"},"page":{"type":"integer","minimum":1.0,"title":"Page","default":1},"page_size":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Page Size","default":20},"updated_after":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated After"},"updated_before":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated Before"},"campaign_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Campaign Ids"},"tag_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Tag Ids"},"sort_order":{"type":"string","enum":["asc","desc"],"title":"Sort Order","default":"desc"},"sort_by":{"type":"string","enum":["updated_at","created_at","last_message_at"],"title":"Sort By","default":"updated_at"},"assigned_to_user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Assigned To User Email"}},"type":"object","title":"CallResultSearchRequest","description":"Filter recorded call outcomes. A POST because the filter is a body."},"CallScriptGenerate":{"properties":{"agent_id":{"type":"string","minLength":1,"title":"Agent Id","description":"The agent whose persona and knowledge shape the script."},"contact_id":{"type":"string","minLength":1,"title":"Contact Id","description":"The contact the call is for; drives memory retrieval."},"context":{"type":"string","minLength":1,"title":"Context","description":"What the call is about."},"prospect_info":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Prospect Info","description":"What you know about the prospect."},"company_context":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Context","description":"What you know about the prospect's company."},"call_objective":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Call Objective","description":"What the call should achieve."},"call_type":{"type":"string","title":"Call Type","description":"professional, casual, cold_call, follow_up, demo or closing.","default":"professional"},"previous_interactions":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Previous Interactions","description":"Summary of earlier conversations."},"provider":{"type":"string","enum":["openai","anthropic","openrouter"],"title":"Provider","description":"LLM provider.","default":"openai"},"model":{"type":"string","title":"Model","description":"openai: gpt-4o or gpt-4o-mini. anthropic: claude-sonnet-4-6, claude-haiku-4-5-20251001 or claude-opus-4-6. Voice rejects any other pairing with a 422.","default":"gpt-4o"}},"type":"object","required":["agent_id","contact_id","context"],"title":"CallScriptGenerate","description":"voice `CallScriptGenerateRequest`, without `org_id` / `agent_settings`."},"CallSummaryRow":{"properties":{"room_name":{"type":"string","title":"Room Name"},"created_at":{"anyOf":[{},{"type":"null"}],"title":"Created At"},"disposition":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Disposition"},"summary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Summary"},"call_duration":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Call Duration"},"recording_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Recording Url"},"parallel_session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Parallel Session Id"},"contact_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contact Id"},"from_":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"From"},"to":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"To"},"has_transcript":{"type":"boolean","title":"Has Transcript","default":false}},"type":"object","required":["room_name"],"title":"CallSummaryRow","description":"Light-weight dialer call summary returned in the dialer-call list.\n\nDeliberately omits the transcript blob - transcripts are 5-50 KB each\nand including them in a list would blow caller context budget. Use\n``has_transcript`` to decide whether a follow-up GET to\n``/voice/dialer/calls/{room_name}/transcript`` is worthwhile.\n\n``contact_id``, ``from_``, and ``to`` are included so client-side\npolling consumers (SDR ingestion pipelines) can filter without an\nextra round-trip for each row."},"CallTranscriptResponse":{"properties":{"room_name":{"type":"string","title":"Room Name"},"status":{"type":"string","title":"Status","description":"ready | empty","default":"ready"},"transcript":{"items":{"$ref":"#/components/schemas/CallTranscriptSegment"},"type":"array","title":"Transcript"},"summary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Summary"},"disposition":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Disposition"},"contact_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contact Id"},"call_duration":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Call Duration"},"recording_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Recording Url"},"parallel_session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Parallel Session Id"},"created_at":{"anyOf":[{},{"type":"null"}],"title":"Created At"}},"type":"object","required":["room_name"],"title":"CallTranscriptResponse","description":"Full transcript payload for a single dialer call.\n\nMirrors the grading response shape: ``status=\"ready\"`` when the\ntranscript has been flushed to the database, ``status=\"empty\"`` when\nthe call row exists but the persistor has not yet written the\ntranscript column (the call may still be in progress or the flush\nmay be in-flight). 404 is raised by the route on a missing row."},"CallTranscriptSegment":{"properties":{"speaker":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Speaker"},"content":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Content"},"timestamp":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Timestamp"}},"type":"object","title":"CallTranscriptSegment","description":"One speaker turn in a persisted dialer transcript.\n\n``speaker`` is one of ``SDR | AI | HUMAN | BOT`` (voice service does\nnot gate the value, so consumers should treat unknown values as\npass-through rather than rejecting the row). ``timestamp`` is the\nvoice-service-emitted ISO-8601 string and may be missing on very\nearly rows that pre-date timestamping in dialer_events.py."},"CallsListResponse":{"properties":{"contact_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contact Id"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email"},"parallel_session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Parallel Session Id"},"count":{"type":"integer","title":"Count","default":0},"calls":{"items":{"$ref":"#/components/schemas/CallSummaryRow"},"type":"array","title":"Calls"}},"type":"object","title":"CallsListResponse","description":"List wrapper for dialer call history.\n\nUsed by ``GET /voice/dialer/calls`` for ALL filter variants\n(contact_id, user_email, parallel_session_id, created_after). Echoes\nthe applied filter values back so callers can sanity-check what the\nserver actually applied (the proxy may pin org_id, normalize CRM\noverlay IDs, etc)."},"CampaignAttachAudienceRequest":{"properties":{"list_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"List Id","description":"List ID to attach as the campaign's audience. Pass null to detach. The list must already exist in this org (matches audiences.id, the canonical lists table — accepts an integer or its string form)."}},"type":"object","title":"CampaignAttachAudienceRequest","description":"Body for PUT /campaigns/{id}/audience — attach (or detach with null) a list."},"CampaignDocumentCreateRequest":{"properties":{"file_type":{"type":"string","title":"File Type","description":"Document type, for example campaign_brief or sequence"},"display_name":{"type":"string","title":"Display Name","description":"Human-readable document name"},"content":{"type":"string","title":"Content","description":"Document content","default":""},"folder_path":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Folder Path","description":"Optional folder path"},"status":{"type":"string","title":"Status","description":"Document status — 'draft' (default) or 'completed'","default":"draft"},"structured_data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Structured Data","description":"Optional structured payload (e.g., sequence steps, persona JSON) stored alongside the markdown content at meta_data.structured_data. Mirrors the update path so the MCP create+update flow is symmetric."}},"type":"object","required":["file_type","display_name"],"title":"CampaignDocumentCreateRequest"},"CampaignDocumentManifestRequest":{"properties":{"campaign_focus":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Focus","default":"outbound"},"channels":{"items":{"type":"string"},"type":"array","title":"Channels"},"execution_targets":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Execution Targets"},"audience_source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience Source"}},"type":"object","required":["channels"],"title":"CampaignDocumentManifestRequest","description":"Preview which documents a campaign would generate. Spends nothing."},"CampaignDocumentUpdateRequest":{"properties":{"content":{"type":"string","title":"Content","description":"Document content","default":""},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"Optional document status"},"structured_data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Structured Data","description":"Optional structured document data"}},"type":"object","title":"CampaignDocumentUpdateRequest"},"CampaignFullPatchDocument":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id","description":"Existing document id. When omitted, a new document is created."},"file_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"File Type","description":"Required when creating; ignored on update of existing id."},"display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display Name","description":"Display name (create only)"},"folder_path":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Folder Path","description":"Folder path (create only)"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"Document status"},"content":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Content","description":"Plain string content (replaces existing meta_data.content)."},"structured_data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Structured Data","description":"Optional structured data, merged into meta_data.structured_data."}},"type":"object","title":"CampaignFullPatchDocument","description":"A single-document patch for `PATCH /campaigns/{id}/full`."},"CampaignFullPatchRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Name"},"brief":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Brief"},"core_concept":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Core Concept"},"primary_hook":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Primary Hook"},"target_persona":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Target Persona"},"category":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Category"},"goal":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Goal"},"audience_list_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience List Id","description":"If provided (including empty string treated as detach), updates audience_list_id. Use the dedicated PUT /audience endpoint when you only need to attach."},"detach_audience":{"type":"boolean","title":"Detach Audience","description":"Set true to explicitly DETACH the audience (audience_list_id=NULL). Required because JSON null in audience_list_id is ambiguous (could mean 'no change').","default":false},"documents":{"anyOf":[{"items":{"$ref":"#/components/schemas/CampaignFullPatchDocument"},"type":"array"},{"type":"null"}],"title":"Documents","description":"Per-document patches. Existing docs are updated in place (id required); new docs are created when id is omitted and file_type+display_name are present."},"sequence_steps":{"anyOf":[{"items":{"$ref":"#/components/schemas/SequenceStepRef"},"type":"array"},{"type":"null"}],"title":"Sequence Steps","description":"If provided, replaces the sequence step ordering (same as PUT /sequence)."},"linked_sequence_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Linked Sequence Ids","description":"Existing sequence IDs to bind to this campaign. INSERTs rows with status='linked' into cb_campaign_sequence_links. Skips IDs that are already linked (any status). Use for pre-launch wiring of an existing sequence; launch writes its own 'pushed' audit rows."},"unlink_sequence_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Unlink Sequence Ids","description":"Sequence IDs to UNLINK from this campaign. DELETEs ONLY rows where status='linked'. Launch-audit rows (status='pushed'/'superseded'/'failed') are never touched — those are an immutable historical record."},"target_channels":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Target Channels","description":"Replace the campaign's channels (email, linkedin, phone, voice_ai, sms). Omit to leave them unchanged. Same as PATCH /campaigns/{id}."}},"type":"object","title":"CampaignFullPatchRequest","description":"Deep-update payload for `PATCH /campaigns/{id}/full`.\n\nEvery field is optional. Each non-null section is applied in the same\ntransaction — campaign fields → audience → documents → sequence — so a\nsingle call can re-shape the whole campaign without ping-pong."},"CampaignGenerationUpdateRequest":{"properties":{"auto_generate_landing_page":{"type":"boolean","title":"Auto Generate Landing Page","description":"Generate a landing page alongside a new campaign.","default":true},"auto_generate_ad_images":{"type":"boolean","title":"Auto Generate Ad Images","description":"Generate ad images alongside a new campaign.","default":true}},"type":"object","title":"CampaignGenerationUpdateRequest","description":"Mirrors `UpdateCampaignGenerationSettingsRequest`.\n\nBoth default to TRUE, so an empty body turns both toggles ON. That is the\napp's shape and it is a real trap: a partial body is not a partial update."},"CampaignLaunchRequest":{"properties":{"sender_mailbox_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Sender Mailbox Ids","description":"Explicit list of mailbox IDs (from GET /mailboxes) to attach as sequence channels before launch. Each ID must reference a connection_status='active', non-archived mailbox in this org. When omitted, the bridge auto-picks the first active email mailbox (ORDER BY id ASC). If no supported sender is available, launch fails before sequence creation."},"disable_auto_pick":{"type":"boolean","title":"Disable Auto Pick","description":"Deprecated safety escape hatch. Launch now rejects True because a consequential action cannot proceed without an active sender.","default":false,"deprecated":true},"textual_agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Textual Agent Name","description":"Voice-service agent identifier (from GET /agents) used for email / social steps. Stamped onto seqsequences.textual_agent_name. Pass the same value as `voice_agent_name` to use one agent across all channels (the common case — the unified Agent row already bundles persona + voice + phone + the attached appointment event)."},"voice_agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Voice Agent Name","description":"Voice-service agent identifier (from GET /agents) used for phone / SMS steps. Stamped onto seqsequences.voice_agent_name. When you want a single agent for all channels, set both this and `textual_agent_name` to the same value."},"schedule_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Schedule Id","description":"Send-window schedule UUID (from GET /schedules). Stamped onto seqsequences.schedule_id. When omitted the sequencer falls back to its org-default send window."},"appointment_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Appointment Id","description":"Calendar event-type ID (from GET /event-types) to attach as the booking link on the sequence. Stamped onto seqsequences.appointment_id. When omitted no booking link is attached and any sequence step referencing `{{booking_link}}` will render the org-default link (or empty)."}},"type":"object","title":"CampaignLaunchRequest","description":"Optional body for ``POST /campaigns/{id}/launch`` — all fields optional.\n\nCallers that POST with no body (or an empty {}) use the first active email\nmailbox for the organization. Callers that want explicit control pass\n``sender_mailbox_ids``. Launch fails before sequence creation when no\nsupported active sender is available.\n\nThe MCP `g8_gtm_launch_campaign` wrapper passes ``sender_mailbox_ids`` when\nDaniel's agent already picked a sender; otherwise the auto-pick fallback\nkeeps the one-shot launch flow working with no extra round-trip."},"CampaignSetPersona":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"title":{"type":"string","maxLength":120,"minLength":1,"title":"Title"},"summary":{"anyOf":[{"type":"string","maxLength":600},{"type":"null"}],"title":"Summary"}},"type":"object","required":["title"],"title":"CampaignSetPersona","description":"A buyer persona, as the lens pass needs to see it."},"CampaignVisitorContact":{"properties":{"contact_id":{"type":"integer","title":"Contact Id","description":"Per-org contact id"},"step_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Step Id","description":"Sequencer step the click was attributed to"},"visits":{"type":"integer","title":"Visits","description":"Click events by this contact in the window"},"last_seen":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Seen","description":"Latest click timestamp (ISO)"},"last_path":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Path","description":"Most recent path this contact clicked to"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Contact full name when resolvable (PII)"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email","description":"Contact work email when resolvable (PII)"},"step_label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Step Label","description":"Human-readable step label when resolvable"}},"type":"object","required":["contact_id","visits"],"title":"CampaignVisitorContact","description":"One row of the Top contacts table.\n\nCarries PII (``name`` / ``email``) for the org's own contacts. Omitted\nentirely from the response when the request passes ``include_contacts=false``."},"CampaignVisitorLink":{"properties":{"host":{"type":"string","title":"Host","description":"Clicked destination host"},"path":{"type":"string","title":"Path","description":"Clicked destination path"},"events":{"type":"integer","title":"Events","description":"Human click events on this URL (scanner-filtered)"},"unique_contacts":{"type":"integer","title":"Unique Contacts","description":"Distinct contacts who clicked this URL"},"last_seen":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Seen","description":"Latest click timestamp (ISO)"},"step_ids":{"items":{"type":"string"},"type":"array","title":"Step Ids","description":"Sequencer steps whose links drove these clicks"},"emails_with_link":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Emails With Link","description":"Sends whose template embedded this URL (CTR denominator)"},"ctr_percent":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Ctr Percent","description":"events ÷ emails_with_link × 100, clamped [0,100]; null when no denominator"},"step_labels":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Step Labels","description":"Human-readable labels for step_ids when resolvable"},"ctr_unavailable_reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Ctr Unavailable Reason","description":"Why `ctr_percent` is null: 'no_matching_send' = no email sent in the window contained this exact link (e.g. the click came from an email sent before the window, or from a link shared outside a sequence); 'send_lookup_unavailable' = the send counts could not be loaded this time. Null whenever `ctr_percent` has a value."}},"type":"object","required":["host","path","events","unique_contacts"],"title":"CampaignVisitorLink","description":"One row of the Email Link Engagement table (a clicked destination URL)."},"CampaignVisitorStep":{"properties":{"step_id":{"type":"string","title":"Step Id","description":"Sequencer step id (globally-unique CUID)"},"events":{"type":"integer","title":"Events","description":"Campaign click events attributed to this step"},"unique_contacts":{"type":"integer","title":"Unique Contacts","description":"Distinct contacts who clicked from this step"},"first_seen":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Seen","description":"Earliest click timestamp (ISO)"},"last_seen":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Seen","description":"Latest click timestamp (ISO)"},"step_label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Step Label","description":"Human-readable '{sequence} / Step {n}' when resolvable"},"emails_sent":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Emails Sent","description":"EMAIL sends dispatched from this step in the window"},"emails_with_link":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Emails With Link","description":"Of those sends, how many carried a link"}},"type":"object","required":["step_id","events","unique_contacts"],"title":"CampaignVisitorStep","description":"One row of the Top campaign steps table."},"CampaignVisitorsMetric":{"properties":{"key":{"type":"string","title":"Key","description":"The `summary` field this entry describes (same value)"},"label":{"type":"string","title":"Label","description":"Human-readable metric name"},"value":{"anyOf":[{"type":"integer"},{"type":"boolean"}],"title":"Value","description":"Same value as `summary.<key>`"},"definition":{"type":"string","title":"Definition","description":"What is counted, in plain language"},"scope":{"type":"string","title":"Scope","description":"'site' = all tracked page views (context only), 'campaign' = email-link clicks, 'diagnostic' = tracking-health detail, 'table' = row counts behind the tables"}},"type":"object","required":["key","label","value","definition","scope"],"title":"CampaignVisitorsMetric","description":"One summary counter with a human label and a plain-language definition.\n\nAdded for VI-04: the raw ``summary`` keys are internal names\n(``jitsu_wired``, ``encrypted_pageviews``) and mix whole-site volume with\ncampaign clicks. ``summary.metrics`` lists the SAME values under friendly\nlabels; the original keys are unchanged."},"CampaignVisitorsReport":{"properties":{"window":{"$ref":"#/components/schemas/CampaignVisitorsWindow"},"summary":{"$ref":"#/components/schemas/CampaignVisitorsSummary"},"top_campaign_steps":{"items":{"$ref":"#/components/schemas/CampaignVisitorStep"},"type":"array","title":"Top Campaign Steps"},"link_engagement":{"items":{"$ref":"#/components/schemas/CampaignVisitorLink"},"type":"array","title":"Link Engagement"},"top_contacts":{"items":{"$ref":"#/components/schemas/CampaignVisitorContact"},"type":"array","title":"Top Contacts"}},"type":"object","required":["window","summary","top_campaign_steps","link_engagement","top_contacts"],"title":"CampaignVisitorsReport","description":"Composite Campaign Visitors report for a single org (analytics report a23)."},"CampaignVisitorsSummary":{"properties":{"total_page_events":{"type":"integer","title":"Total Page Events","description":"All page events in the window (campaign + non-campaign)"},"pageview_events":{"type":"integer","title":"Pageview Events","description":"Parseable campaign-attributed click events"},"unique_contacts":{"type":"integer","title":"Unique Contacts","description":"Distinct contacts who clicked a campaign link"},"unique_campaign_steps":{"type":"integer","title":"Unique Campaign Steps","description":"Distinct sequencer steps that drew clicks"},"identified_visitors":{"type":"integer","title":"Identified Visitors","description":"Distinct identified web sessions on campaign clicks"},"jitsu_wired":{"type":"boolean","title":"Jitsu Wired","description":"False when the org has no visitor-tracking pipeline / no page events"},"unparseable_pageviews":{"type":"integer","title":"Unparseable Pageviews","description":"Campaign clicks whose tracking hash could not be decoded"},"encrypted_pageviews":{"type":"integer","title":"Encrypted Pageviews","description":"Diagnostic: campaign clicks with an encrypted (#c=e1.) hash"},"plaintext_pageviews":{"type":"integer","title":"Plaintext Pageviews","description":"Diagnostic: campaign clicks with a plaintext hash"},"contact_rows":{"type":"integer","title":"Contact Rows","description":"Total (contact, step) click groups before the `limit` cap"},"step_rows":{"type":"integer","title":"Step Rows","description":"Total distinct campaign steps before the `limit` cap"},"link_rows":{"type":"integer","title":"Link Rows","description":"Total distinct clicked (host, path) before the ceiling"},"metrics":{"items":{"$ref":"#/components/schemas/CampaignVisitorsMetric"},"type":"array","title":"Metrics","description":"The counters above with friendly labels, plain-language definitions and a scope, in display order. Same values as the individual keys; use this to present the summary."}},"type":"object","required":["total_page_events","pageview_events","unique_contacts","unique_campaign_steps","identified_visitors","jitsu_wired","unparseable_pageviews","encrypted_pageviews","plaintext_pageviews","contact_rows","step_rows","link_rows"],"title":"CampaignVisitorsSummary","description":"KPI tiles for the org's campaign-click activity in the window.\n\nAll click-derived counters are email-security-scanner filtered (humans only)\nwhen ``SEQUENCER_VISITOR_SCANNER_FILTER=enforce`` — the same honest counts the\nin-app report shows. ``total_page_events`` is all page volume (not filtered)."},"CampaignVisitorsWindow":{"properties":{"start_date":{"type":"string","title":"Start Date","description":"Window start (inclusive), YYYY-MM-DD"},"end_date":{"type":"string","title":"End Date","description":"Window end (inclusive), YYYY-MM-DD"},"days":{"type":"integer","title":"Days","description":"Inclusive calendar-day span of the window"},"mode":{"type":"string","title":"Mode","description":"'anchored' (explicit start/end) or 'rolling' (last-N-days)"}},"type":"object","required":["start_date","end_date","days","mode"],"title":"CampaignVisitorsWindow","description":"The resolved reporting window echoed back to the caller."},"CampaignWorkflowLinkUpdateRequest":{"properties":{"role":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Role"},"display_order":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Display Order"},"status":{"anyOf":[{"type":"string","enum":["active","paused","archived"]},{"type":"null"}],"title":"Status"}},"type":"object","title":"CampaignWorkflowLinkUpdateRequest"},"CampaignWorkflowListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"CampaignWorkflowListPayload","description":"A campaign's workflow links under `items`."},"CampaignWorkflowPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"CampaignWorkflowPayload","description":"A campaign-workflow link, generation progress or save result."},"CancelAgentRunResponse":{"properties":{"work_item_id":{"type":"string","title":"Work Item Id"},"cancelled":{"type":"boolean","title":"Cancelled"},"children_cancelled":{"items":{"type":"string"},"type":"array","title":"Children Cancelled","description":"Sub-agents signalled alongside the run."},"detail":{"type":"string","title":"Detail","default":""}},"type":"object","required":["work_item_id","cancelled"],"title":"CancelAgentRunResponse"},"CancelBookingRequest":{"properties":{"cancellation_reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Cancellation Reason"},"cancel_subsequent":{"type":"boolean","title":"Cancel Subsequent","default":false}},"type":"object","title":"CancelBookingRequest"},"ChannelConfig":{"properties":{"channel_id":{"type":"integer","title":"Channel Id","description":"Channel resource ID (mailbox ID, phone ID, etc.)"},"channel_value":{"type":"string","title":"Channel Value","description":"Channel value (email address, phone number, etc.)"},"channel_type":{"type":"string","title":"Channel Type","description":"Channel type. One of: SMTP, GMAIL, INBOXKIT, PHONE, LINKEDIN, SMS, WHATSAPP. Case-insensitive."},"channel_data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Channel Data","description":"Extra channel metadata"}},"type":"object","required":["channel_id","channel_value","channel_type"],"title":"ChannelConfig"},"ChannelPreferenceRequest":{"properties":{"key":{"type":"string","title":"Key","description":"Preference key, from GET /channels/preferences"},"value":{"title":"Value","description":"New value. The service rejects a value the key does not accept with a 422."}},"type":"object","required":["key","value"],"title":"ChannelPreferenceRequest","description":"Set ONE org-wide channel preference."},"ChannelSettingsRule":{"properties":{"enabled":{"type":"boolean","title":"Enabled","default":true},"monthly_credit_cap":{"type":"integer","minimum":0.0,"title":"Monthly Credit Cap","default":0},"per_poll_result_cap":{"type":"integer","minimum":0.0,"title":"Per Poll Result Cap","default":50},"max_comments_per_post":{"type":"integer","minimum":0.0,"title":"Max Comments Per Post","default":50},"max_reactions_per_post":{"type":"integer","minimum":0.0,"title":"Max Reactions Per Post","default":100},"fetch_engagements":{"type":"boolean","title":"Fetch Engagements","description":"Fetch who engaged with each matched post. Multiplies what a poll costs.","default":false}},"type":"object","title":"ChannelSettingsRule","description":"Per-channel spend and volume ceilings."},"ChartOther":{"properties":{"group_count":{"type":"integer","title":"Group Count"},"record_count":{"type":"integer","title":"Record Count"},"measures":{"additionalProperties":{"anyOf":[{"type":"number"},{"type":"integer"},{"type":"null"}]},"type":"object","title":"Measures"}},"type":"object","required":["group_count","record_count","measures"],"title":"ChartOther","description":"What the chart folds into \"Other\": every group beyond ``chart_limit``. Only additive measures (count, sum,\nrelated_count) are filled in; an average, minimum or maximum cannot be folded and is None."},"ChatBotCreateRequest":{"properties":{"name":{"type":"string","maxLength":120,"minLength":1,"title":"Name"},"agent_id":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Agent Id","description":"Optional voice/text agent id used to seed the new bot's external chat agent. When omitted, no agent row is created."},"agent_name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Agent Name","description":"Display name of the selected agent. Stored on the agent row so the widget shows the AGENT's name, not the bot's. Falls back to the bot name when omitted."}},"type":"object","required":["name"],"title":"ChatBotCreateRequest","description":"A new chat bot.\n\nAn org can run several. `chat_bot_id` is REQUIRED on almost every other\ncall on this surface because the same org's agents, buttons, questions,\nblogs and theme are all per-bot - so create one of these first, or read the\norg's existing bots from `GET /webchat/chat-bots`."},"ChatBotUpdateRequest":{"properties":{"name":{"type":"string","maxLength":120,"minLength":1,"title":"Name"},"expected_revision":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Expected Revision","description":"Revision you last read. Omit to overwrite unconditionally."}},"type":"object","required":["name"],"title":"ChatBotUpdateRequest","description":"Rename a chat bot.\n\n`name` is REQUIRED even though this is a PATCH - it is the only mutable\nfield, and the app's model requires it. `expected_revision` is the\noptimistic-concurrency check: send the revision you read, and a concurrent\nedit comes back 409 rather than silently overwriting."},"ChatSearchRequest":{"properties":{"user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Id","description":"Restrict to one user's chats."},"page":{"type":"integer","minimum":1.0,"title":"Page","default":1},"page_size":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Page Size","default":20},"updated_after":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated After"},"updated_before":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated Before"},"sort_order":{"type":"string","enum":["asc","desc"],"title":"Sort Order","default":"desc"},"sort_by":{"type":"string","enum":["updated_at","created_at","last_message_at"],"title":"Sort By","description":"Field to sort by. See `SortByField` for the accepted values.","default":"created_at"},"tags":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Tags","description":"Keep chats carrying ANY of these tag ids."},"exclude_tag_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Exclude Tag Ids","description":"Drop chats carrying ANY of these tag ids. This is what makes a Focused view work - the app sends the archived/deleted/warmup/bounced tags here. Without it those threads come back."}},"type":"object","title":"ChatSearchRequest","description":"Filter and page the chat inbox."},"ChatStarRequest":{"properties":{"is_starred":{"type":"boolean","title":"Is Starred"}},"type":"object","required":["is_starred"],"title":"ChatStarRequest","description":"Set, rather than toggle, the starred state.\n\nDeclared as a required bool for exactly that reason: a toggle is not\nidempotent, so a retried request would silently un-star the thread it just\nstarred."},"CheckImportDuplicatesRequest":{"properties":{"column_mapping":{"additionalProperties":{"type":"string"},"type":"object","title":"Column Mapping","description":"Source column -> graph8 field, the same mapping you intend to import with."},"entity_type":{"type":"string","enum":["contact","company"],"title":"Entity Type","description":"`contact` matches on work email; `company` matches on domain.","default":"contact"}},"type":"object","title":"CheckImportDuplicatesRequest","description":"Which uploaded rows already exist in graph8."},"ChooseRelatedRecordRequest":{"properties":{"contact_id":{"type":"integer","exclusiveMinimum":0.0,"title":"Contact Id"},"definition_id":{"type":"string","format":"uuid","title":"Definition Id","description":"The relationship definition the record is linked through."},"record_id":{"type":"string","format":"uuid","title":"Record Id","description":"The linked custom-object record whose fields personalise this contact's sends."}},"type":"object","required":["contact_id","definition_id","record_id"],"title":"ChooseRelatedRecordRequest"},"ClaimDomainRequest":{"properties":{"hostname":{"type":"string","maxLength":253,"title":"Hostname","description":"The hostname to serve this app on. Normalized server-side: case, a trailing dot and unicode all resolve to one canonical form."}},"type":"object","required":["hostname"],"title":"ClaimDomainRequest"},"ClickhouseMashupRequest":{"properties":{"mode":{"type":"string","enum":["by_upid","by_hem","by_domain"],"title":"Mode","description":"Which mashup PK to filter by."},"values":{"items":{"type":"string"},"type":"array","maxItems":100,"minItems":1,"title":"Values","description":"Up to 100 key values (UP_IDs, HEMs, or domains)."},"profile":{"type":"string","enum":["b2b","b2c","joined"],"title":"Profile","description":"Which mashup table to read. 'joined' returns the denormalized contact+company record from the current mashup build (mashup.v3_enriched_for_os); by_domain mode only.","default":"b2b"},"limit":{"type":"integer","maximum":1000.0,"minimum":1.0,"title":"Limit","default":1000}},"type":"object","required":["mode","values"],"title":"ClickhouseMashupRequest"},"ClickhouseMashupResponse":{"properties":{"mode":{"type":"string","title":"Mode"},"profile":{"type":"string","title":"Profile"},"records":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Records","default":[]},"matched":{"type":"integer","title":"Matched","default":0},"requested":{"type":"integer","title":"Requested","default":0}},"type":"object","required":["mode","profile"],"title":"ClickhouseMashupResponse"},"ClickhouseOrgAnalyticsRequest":{"properties":{"dataset":{"type":"string","enum":["people_visitors","company_visitors","5x5_visitors","intent_resolved"],"title":"Dataset","description":"Which per-org table to read."},"since":{"type":"string","title":"Since","description":"ISO date or datetime (inclusive lower bound)."},"until":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Until","description":"ISO date or datetime (exclusive upper bound). Defaults to now."},"filters":{"additionalProperties":true,"type":"object","title":"Filters","description":"Optional equality filters. Keys must match dataset columns; unknown columns are silently dropped so an LLM guess can't produce a SQL error."},"aggregation":{"type":"string","enum":["raw","daily_counts","top_n"],"title":"Aggregation","description":"'raw' returns the matching rows (capped). 'daily_counts' returns {day, count}. 'top_n' returns {value, count} grouped by the dataset's primary group key (contact_id, company_id, keyword_id).","default":"raw"},"limit":{"type":"integer","maximum":1000.0,"minimum":1.0,"title":"Limit","default":1000}},"type":"object","required":["dataset","since"],"title":"ClickhouseOrgAnalyticsRequest"},"ClickhouseOrgAnalyticsResponse":{"properties":{"dataset":{"type":"string","title":"Dataset"},"aggregation":{"type":"string","title":"Aggregation"},"rows":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Rows","default":[]},"total":{"type":"integer","title":"Total","default":0},"window":{"additionalProperties":{"type":"string"},"type":"object","title":"Window","default":{}}},"type":"object","required":["dataset","aggregation"],"title":"ClickhouseOrgAnalyticsResponse"},"CloneHomepageRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"goal":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Goal"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"use_vision":{"type":"boolean","title":"Use Vision","default":true}},"type":"object","title":"CloneHomepageRequest","description":"Clone the org's own homepage into an editable page. SPENDS CREDIT."},"CloneHtmlRequest":{"properties":{"html":{"type":"string","maxLength":2000000,"minLength":16,"title":"Html"},"filename":{"anyOf":[{"type":"string","maxLength":300},{"type":"null"}],"title":"Filename","description":"Original filename - drives format detection (e.g. dialer.astro)."},"source_url":{"anyOf":[{"type":"string","maxLength":2048},{"type":"null"}],"title":"Source Url"},"name":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Name"},"use_vision":{"type":"boolean","title":"Use Vision","default":false}},"type":"object","required":["html"],"title":"CloneHtmlRequest","description":"Clone from raw source the caller already has. SPENDS CREDIT.\n\n`use_vision` defaults OFF here, unlike `/clone-url`: there is no live page\nto screenshot, so the extra pass buys much less."},"CloneUrlRequest":{"properties":{"url":{"type":"string","maxLength":2048,"minLength":1,"title":"Url"},"name":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Name"},"use_vision":{"type":"boolean","title":"Use Vision","description":"Multimodal pass. Costs more. Default on.","default":true}},"type":"object","required":["url"],"title":"CloneUrlRequest","description":"Clone any public URL into an editable page. SPENDS CREDIT.\n\nIt fetches the page and runs an extraction pass; `use_vision` adds a\nmultimodal pass on a screenshot, which costs more and is the default\nbecause it is what makes the clone usable."},"CloseReasonCreateRequest":{"properties":{"kind":{"type":"string","title":"Kind","description":"Which list this reason belongs to, e.g. won or lost."},"label":{"type":"string","maxLength":255,"minLength":1,"title":"Label"}},"type":"object","required":["kind","label"],"title":"CloseReasonCreateRequest","description":"Add a close reason.\n\nAdding one is gated on `_REASON_MUTATE_PERMISSIONS` (the app's own route\ngate): deliberately wider than the manager tier - a rep extends the list\ninline while closing their own deal - but NOT open to org members with no\ndeal access. REMOVING one carries the same entry gate plus a creator-or-\nmanager check, because manager-only removal would make every rep's typo\npermanent and org-wide."},"CloseReasonListResponse":{"properties":{"reasons":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Reasons"},"can_manage":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Can Manage","description":"Whether this caller may archive reasons they did not create."}},"additionalProperties":true,"type":"object","title":"CloseReasonListResponse","description":"The close reasons, plus what this caller may do with them.\n\n`can_manage` is returned alongside the list ON PURPOSE: it is resolved by\nthe same rule the archive endpoint enforces, so a UI cannot render a delete\ncontrol the backend would refuse - or hide one it would allow."},"CoachListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"CoachListPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape."},"CoachPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"CoachPayload","description":"An open envelope for a call, an interview round or an attempt."},"Collection":{"properties":{"event_id":{"type":"string","maxLength":200,"minLength":1,"title":"Event Id"},"invoice_line_id":{"type":"string","maxLength":200,"minLength":1,"title":"Invoice Line Id"},"customer_id":{"type":"string","maxLength":200,"minLength":1,"title":"Customer Id"},"cohort_id":{"type":"string","maxLength":200,"minLength":1,"title":"Cohort Id"},"product_id":{"type":"string","maxLength":200,"minLength":1,"title":"Product Id"},"paid_month":{"type":"integer","minimum":1.0,"title":"Paid Month"},"collected_on":{"type":"string","format":"date","title":"Collected On"},"currency":{"type":"string","const":"USD","title":"Currency","default":"USD"},"eligible_amount":{"anyOf":[{"type":"number","exclusiveMinimum":0.0},{"type":"string"}],"title":"Eligible Amount"},"quality_approved":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Quality Approved"},"evidence":{"type":"string","maxLength":4000,"minLength":1,"title":"Evidence"},"quality_evidence":{"type":"string","maxLength":2000,"title":"Quality Evidence","default":""},"full_collection":{"type":"boolean","title":"Full Collection","default":false},"verified":{"type":"boolean","const":true,"title":"Verified"}},"additionalProperties":false,"type":"object","required":["event_id","invoice_line_id","customer_id","cohort_id","product_id","paid_month","collected_on","eligible_amount","evidence","verified"],"title":"Collection"},"CollectionCreateRequest":{"properties":{"name":{"type":"string","maxLength":100,"minLength":2,"title":"Name","description":"Collection name."},"description":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Description","description":"What this collection holds."}},"type":"object","required":["name"],"title":"CollectionCreateRequest","description":"A new knowledge collection. Bounds mirror voice's own `Query` limits."},"CollectionFolder":{"properties":{"folder_path":{"type":"string","maxLength":512,"minLength":1,"title":"Folder Path","description":"e.g. `pricing/2026`."}},"type":"object","required":["folder_path"],"title":"CollectionFolder","description":"The folder to create. Voice binds `folder_path` as a query parameter;\nit is a body field here so a path with slashes needs no URL escaping."},"CollectionPasteText":{"properties":{"filename":{"type":"string","minLength":1,"title":"Filename","description":"Given no extension, `.txt` is appended."},"text_content":{"type":"string","minLength":1,"title":"Text Content"},"folder_path":{"type":"string","title":"Folder Path","description":"Folder inside the collection. Empty is the root.","default":""}},"type":"object","required":["filename","text_content"],"title":"CollectionPasteText","description":"`POST .../files/paste-text` binds its body as FORM fields (`org_id`,\n`folder_path`, `filename`, `text_content`); this is the JSON shape the API\ntakes, with `org_id` injected from the key."},"CollectionSearch":{"properties":{"query":{"type":"string","minLength":1,"title":"Query"},"collection_ids":{"items":{"type":"integer"},"type":"array","maxItems":20,"minItems":1,"title":"Collection Ids","description":"Collections to search (1-4 is best)."},"top_k":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Top K","description":"Results per collection.","default":15}},"type":"object","required":["query","collection_ids"],"title":"CollectionSearch","description":"voice `CollectionSearchRequest`, without `org_id`."},"CollectionUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":100,"minLength":2},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Description"}},"type":"object","title":"CollectionUpdateRequest","description":"Rename or re-describe a collection. Omit a field to leave it alone."},"ColorSwap":{"properties":{"from_color":{"type":"string","pattern":"^#(?:[0-9a-fA-F]{3}|[0-9a-fA-F]{4}|[0-9a-fA-F]{6}|[0-9a-fA-F]{8})$","title":"From Color"},"to_color":{"type":"string","pattern":"^#(?:[0-9a-fA-F]{3}|[0-9a-fA-F]{4}|[0-9a-fA-F]{6}|[0-9a-fA-F]{8})$","title":"To Color"}},"type":"object","required":["from_color","to_color"],"title":"ColorSwap","description":"One colour replaced by another, both as hex."},"Column":{"properties":{"id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Id"},"title":{"type":"string","title":"Title"},"data_type":{"$ref":"#/components/schemas/ColumnType","default":"text"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"object_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Object Id"},"source":{"$ref":"#/components/schemas/ColumnSource","default":"contact"},"is_global":{"type":"boolean","title":"Is Global","description":"Automatically computed: True if object_id is None/empty, False otherwise.","readOnly":true},"label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Label","description":"Human-readable display name (CF-09), e.g. ``CONTACT_FIRST_NAME`` ->\n\"First name\", ``COMPANY_NAICS`` -> \"Company NAICS\". Custom columns keep\ntheir own title. Additive and read-only: ``name`` / ``title`` stay the\nstorage key, because callers send them back as identifiers.","readOnly":true}},"additionalProperties":false,"type":"object","required":["title","is_global","label"],"title":"Column","description":"Column entity representing a database column definition.\nUsed to describe table column metadata for MashupContact and other entities."},"ColumnConfigDto":{"properties":{"mode":{"type":"string","title":"Mode","description":"'all' copies every column; 'selected' uses the list below.","default":"all"},"selected_column_ids":{"items":{"type":"string"},"type":"array","title":"Selected Column Ids"},"static_values":{"additionalProperties":{"type":"string"},"type":"object","title":"Static Values"}},"type":"object","title":"ColumnConfigDto","description":"Which columns travel with a routed record."},"ColumnFillRatesResponse":{"properties":{"view":{"type":"string","enum":["companies","contacts"],"title":"View"},"lifecycle_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Lifecycle Id","description":"The stage measured; null = every company (All view)."},"available":{"type":"boolean","title":"Available","description":"False when the measurement failed or timed out; the grid keeps its defaults."},"total":{"type":"integer","title":"Total","description":"Records measured (the stage, or its sample when `sampled`).","default":0},"sampled":{"type":"boolean","title":"Sampled","description":"True when a large stage was measured on a block sample.","default":false},"fill_rates":{"additionalProperties":{"type":"number"},"type":"object","title":"Fill Rates","description":"colId -> share of records (0..1) with a value in that column."},"has_website_tracking":{"type":"boolean","title":"Has Website Tracking","description":"Whether any company or contact of the org recorded a visitor session.","default":true},"computed_at":{"type":"string","title":"Computed At"}},"type":"object","required":["view","available","computed_at"],"title":"ColumnFillRatesResponse"},"ColumnMappingDto":{"properties":{"source_field":{"type":"string","title":"Source Field"},"target_column":{"type":"string","title":"Target Column"}},"type":"object","required":["source_field","target_column"],"title":"ColumnMappingDto","description":"Map a search result field onto a destination column."},"ColumnSource":{"type":"string","enum":["contact","company","custom"],"title":"ColumnSource","description":"Which entity a field in the contact field list belongs to.\n\nThe ``GET /contacts/columns`` response deliberately combines fields from\nthree provenances into one list (issue #21184): the person record, their\nemployer's company record, and user-created custom columns. Consumers\n(form-mapping UI, AI-agent field listing, CSV import) need to tell them\napart — a company field like ``COMPANY_REVENUE`` describes the employer,\nnot the contact.\n\n- ``contact``: a field on the person record (``MashupContact.*``) — the default.\n- ``company``: a field on the contact's employer (``MashupCompany.*``),\n  surfaced so contacts can be mapped/filtered by company attributes.\n- ``custom``: a user-created dynamic column (global or list-scoped)."},"ColumnType":{"type":"string","enum":["text","int","numeric","boolean"],"title":"ColumnType","description":"User-selectable dynamic-column data types.\n\nEvery member must have a physical type in the repos' pg_type_map\n(contacts/companies CDP repos + enrichment DynamicColumnRepository:\nint→INTEGER, numeric→NUMERIC, text→TEXT, boolean→BOOLEAN) and belong to\nthe user-owned family in lists/usecases/dynamic_column_write_contract.py —\nboth already list these four. Write paths coerce values per type via\nshared.infrustructure.db.cdp.dynamic_column_values.coerce_dynamic_value."},"CommentAttachmentRef":{"properties":{"token":{"type":"string","maxLength":8192,"title":"Token"},"key":{"type":"string","maxLength":1024,"title":"Key"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"size":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Size"},"type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Type"}},"type":"object","required":["token","key"],"title":"CommentAttachmentRef","description":"A file already uploaded to the private note namespace.\n\nOnly `token` and `key` are load-bearing: the server re-validates the\ncapability token and never trusts the name, size or type a client sends.\nThey are accepted because the app's model accepts them."},"CommentCreateRequest":{"properties":{"content":{"type":"string","maxLength":5000,"minLength":1,"title":"Content"},"attachments":{"items":{"$ref":"#/components/schemas/CommentAttachmentRef"},"type":"array","title":"Attachments"},"mentioned_user_ids":{"items":{"type":"string"},"type":"array","title":"Mentioned User Ids","description":"Mentioned users by id. Each gets a Work task."},"mentioned_user_emails":{"items":{"type":"string"},"type":"array","title":"Mentioned User Emails","description":"The same users by email. Additive - this is what drives the notification."}},"type":"object","required":["content"],"title":"CommentCreateRequest","description":"An INTERNAL note on a conversation. The customer never sees it.\n\nMentioning someone creates them a task in the Work app. The two mention\nlists are ADDITIVE rather than alternatives: an id with no matching email\nstill gets the task, it just gets no notification - so sending both is how\nyou get the bell as well."},"CommissionConfig":{"properties":{"mode":{"type":"string","enum":["none","per_meeting"],"title":"Mode","default":"none"},"per_meeting_rate":{"type":"number","minimum":0.0,"title":"Per Meeting Rate","default":0.0},"per_employee_overrides":{"additionalProperties":{"$ref":"#/components/schemas/EmployeeCommissionOverride"},"type":"object","title":"Per Employee Overrides"}},"type":"object","title":"CommissionConfig","description":"Commission model. v1 supports ``none`` and ``per_meeting`` only —\n``revenue_pct`` needs per-rep deal attribution we don't have cleanly yet\n(Phase 2), so it is rejected by the validator."},"CommitteeCreateRequest":{"properties":{"name":{"type":"string","title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"is_default":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Default","description":"Make this the org's default committee (unsets the previous one).","default":false}},"type":"object","required":["name"],"title":"CommitteeCreateRequest"},"CommitteeEditRequest":{"properties":{"add":{"items":{"$ref":"#/components/schemas/CommitteeMemberInput"},"type":"array","title":"Add"},"remove":{"items":{"type":"integer"},"type":"array","title":"Remove","description":"Contact ids to take off the committee."}},"type":"object","title":"CommitteeEditRequest","description":"Add and remove buying-committee members in one call.\n\nA committee edit rides plan versioning like everything else: it persists a\nNEW plan version, preserving the existing steps. Both lists are applied in\nthe same version, so adding and removing in one request cannot leave the\ncommittee half-changed."},"CommitteeLinkedInInviteRequest":{"properties":{"note":{"anyOf":[{"type":"string","maxLength":300},{"type":"null"}],"title":"Note","description":"Optional invite note. Capped by LinkedIn at 300 characters."}},"type":"object","title":"CommitteeLinkedInInviteRequest","description":"The optional note on a LinkedIn connection request.\n\n300 characters is LinkedIn's own cap, not a display limit."},"CommitteeMemberAssignment":{"properties":{"persona_id":{"type":"string","title":"Persona Id"},"abm_category":{"anyOf":[{"type":"string","enum":["economic_buyer","champion","end_user","technical"]},{"type":"null"}],"title":"Abm Category","description":"The role slot. Null keeps the persona on the committee with no role."}},"type":"object","required":["persona_id"],"title":"CommitteeMemberAssignment"},"CommitteeMemberInput":{"properties":{"contact_id":{"type":"integer","title":"Contact Id"},"role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Role","description":"Their part in the decision, e.g. \"champion\"."}},"type":"object","required":["contact_id"],"title":"CommitteeMemberInput","description":"A contact to put on the buying committee."},"CommitteeMembersRequest":{"properties":{"members":{"items":{"$ref":"#/components/schemas/CommitteeMemberAssignment"},"type":"array","title":"Members","description":"The FULL roster. Personas left out are removed from the committee."}},"type":"object","required":["members"],"title":"CommitteeMembersRequest"},"CommitteeUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"is_default":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Default"}},"type":"object","title":"CommitteeUpdateRequest"},"CompaniesOpenJobsRequest":{"properties":{"company_ids":{"items":{"type":"integer"},"type":"array","maxItems":200,"minItems":1,"title":"Company Ids","description":"CRM company IDs (mashup_companies.id) - NOT linkedin_company_id"},"window_days":{"type":"integer","maximum":365.0,"minimum":1.0,"title":"Window Days","default":60},"include_postings":{"type":"boolean","title":"Include Postings","description":"False = counts only (one CH query)","default":true},"limit_per_company":{"type":"integer","maximum":50.0,"minimum":1.0,"title":"Limit Per Company","default":25},"include_subsidiaries":{"type":"boolean","title":"Include Subsidiaries","description":"Roll subsidiary postings into the parent. Off by default: one row = one company. NOTE: when true, `jobs` expands to child companies but `open_jobs` stays parent-only, so len(jobs) can exceed open_jobs.","default":false}},"type":"object","required":["company_ids"],"title":"CompaniesOpenJobsRequest","description":"Request contract for the hiring-signal batch lookup.\n\nField-for-field identical to the main-app model of the same name in\n``companies/interfaces/fastapi/router.py``. It is redefined here rather\nthan imported because that module imports\n``developer_api.dependencies.hybrid_auth``; importing it back would couple\nthe two app halves at import time. ``test_companies_open_jobs_api.py`` locks\nthe two models together so the duplication cannot silently drift."},"CompanyAssertRequest":{"properties":{"list_id":{"type":"integer","title":"List Id","description":"Target list ID"},"domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain","description":"Company domain (primary match key)"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url","description":"LinkedIn URL (fallback match key)"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"industry":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Industry"},"employee_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Employee Count"},"annual_revenue":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Annual Revenue"},"city":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"City"},"state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"State"},"country":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country"},"website":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Website"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"custom_fields":{"anyOf":[{"additionalProperties":{"anyOf":[{"type":"string"},{"type":"null"}]},"type":"object"},{"type":"null"}],"title":"Custom Fields","description":"Custom column values to write on this record, keyed by the column's display title (e.g. 'Followup 1'), its slug (e.g. 'udo_followup_1_ab12cd34'), or a case/space variant of the title. Keys that match no existing column are reported back in `ignored_fields` unless `create_missing_fields` is true."},"create_missing_fields":{"type":"boolean","title":"Create Missing Fields","description":"When true, any key in `custom_fields` that matches no existing column is created as a NEW list-scoped custom column (max 100 per request) and then written. Default false preserves the previous behaviour of not creating columns implicitly.","default":false}},"type":"object","required":["list_id"],"title":"CompanyAssertRequest"},"CompanyAssertResponse":{"properties":{"action":{"type":"string","title":"Action","description":"'created' or 'updated'"},"count":{"type":"integer","title":"Count","default":1},"custom_fields":{"$ref":"#/components/schemas/CustomFieldWriteReport"},"warnings":{"items":{"type":"string"},"type":"array","title":"Warnings","description":"Advisory notes about values saved as sent that look wrong (e.g. an unrecognised country). Empty when the input is clean."},"company_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Company Id","description":"ID of the company that was created or updated (use it with GET/PATCH /companies/{company_id}). Null when the saved record cannot be identified unambiguously, e.g. when the domain already matched several companies in the list."}},"type":"object","required":["action"],"title":"CompanyAssertResponse"},"CompanyContactImport":{"properties":{"email":{"type":"string","title":"Email","description":"Email address. Also the company-grouping key."},"first_name":{"type":"string","title":"First Name","description":"First name."},"last_name":{"type":"string","title":"Last Name","description":"Last name."},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title","description":"Job title."},"phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone","description":"Phone number."},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url","description":"LinkedIn profile URL."},"company_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Name","description":"Company name, used only when the domain is unknown."},"role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Role","description":"Buying-committee role: decision_maker | influencer | champion | end_user | blocker | coach."},"contact_owner":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contact Owner","description":"Contact owner."},"company_owner":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Owner","description":"Company owner."}},"type":"object","required":["email","first_name","last_name"],"title":"CompanyContactImport","description":"One contact in a company import.\n\nContacts are grouped by email domain, so `email` decides which company a\nrow lands on - `company_name` only names a company that does not exist yet."},"CompanyContactItem":{"properties":{"id":{"type":"integer","title":"Id"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"full_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Full Name"},"work_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Work Email"},"job_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Title"},"seniority_level":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Seniority Level"},"direct_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Direct Phone"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url"},"city":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"City"},"state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"State"},"country":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country"}},"type":"object","required":["id"],"title":"CompanyContactItem","description":"Contact summary within a company."},"CompanyContactScoreDTO":{"properties":{"contact_id":{"type":"integer","title":"Contact Id"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"score":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Score"},"classification":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Classification"},"responded":{"type":"boolean","title":"Responded","default":false},"last_responded_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Responded At"},"trend":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Trend"},"history":{"items":{"$ref":"#/components/schemas/SurveyScorePointDTO"},"type":"array","title":"History","default":[]}},"type":"object","required":["contact_id"],"title":"CompanyContactScoreDTO"},"CompanyCreateRequest":{"properties":{"domain":{"type":"string","title":"Domain","description":"Company domain, e.g. acme.com (required)"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"website":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Website"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone"},"address":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Address"},"city":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"City"},"state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"State"},"country":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country"},"zip":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Zip"},"industry":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Industry"},"employee_count":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Employee Count"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id","description":"Optional list to add the company to after creation"}},"type":"object","required":["domain"],"title":"CompanyCreateRequest","description":"Request body for creating a company.\n\n``domain`` is required — it drives dedup (an existing company with the same\ndomain is reused, not duplicated) and the Deals company picker. Every other\nfield is optional."},"CompanyCreateResponse":{"properties":{"status":{"type":"string","title":"Status"},"company_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Company Id"},"merged":{"type":"boolean","title":"Merged","default":false},"warnings":{"items":{"type":"string"},"type":"array","title":"Warnings","description":"Advisory notes about values that look wrong (e.g. an employee_count with no number, an unrecognised country, or a linkedin_url that is not a web address and was not saved). Empty when the input is clean."}},"type":"object","required":["status"],"title":"CompanyCreateResponse"},"CompanyJobCountsRequest":{"properties":{"linkedin_company_ids":{"items":{"type":"integer"},"type":"array","maxItems":1000,"title":"Linkedin Company Ids","description":"LinkedIn company ids (lcids). Capped at 1000 - one grid page, not a corpus scan."},"window_days":{"type":"integer","maximum":365.0,"minimum":1.0,"title":"Window Days","default":60}},"type":"object","title":"CompanyJobCountsRequest","description":"Active-job counts for a page of companies."},"CompanyListItem":{"properties":{"id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain"},"website":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Website"},"industry":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Industry"},"employee_count":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Employee Count"},"revenue":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Revenue"},"founded_year":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Founded Year"},"city":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"City"},"state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"State"},"country":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url"},"linkedin_followers":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Followers"},"logo_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Logo Url"},"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id"},"owner_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Name"},"custom_fields":{"anyOf":[{"additionalProperties":{"anyOf":[{"type":"string"},{"type":"null"}]},"type":"object"},{"type":"null"}],"title":"Custom Fields"}},"type":"object","title":"CompanyListItem","description":"Lighter company representation for list endpoints."},"CompanyLookupRequest":{"properties":{"domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain","description":"Company domain"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Company name"}},"type":"object","title":"CompanyLookupRequest"},"CompanyNpsDTO":{"properties":{"company_id":{"type":"integer","title":"Company Id"},"nps_score":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Nps Score"},"promoters":{"type":"integer","title":"Promoters"},"passives":{"type":"integer","title":"Passives"},"detractors":{"type":"integer","title":"Detractors"},"total_respondents":{"type":"integer","title":"Total Respondents"},"coverage":{"$ref":"#/components/schemas/CoverageDTO"},"suppressed":{"type":"boolean","title":"Suppressed"},"contacts":{"items":{"$ref":"#/components/schemas/CompanyContactScoreDTO"},"type":"array","title":"Contacts"},"bucket":{"type":"string","title":"Bucket"},"time_series":{"items":{"$ref":"#/components/schemas/TrendBarDTO"},"type":"array","title":"Time Series"}},"type":"object","required":["company_id","promoters","passives","detractors","total_respondents","coverage","suppressed","contacts","bucket","time_series"],"title":"CompanyNpsDTO"},"CompanyProfileUpdateRequest":{"properties":{"website_url":{"type":"string","title":"Website Url","description":"The client's real website. This is the source of truth Studio generation reads; setting it wrong is what makes every downstream ICP, persona and campaign describe the wrong company."},"fields":{"additionalProperties":{"type":"string"},"type":"object","title":"Fields","description":"Profile fields to save, e.g. {'company_name': 'Acme', 'industry': 'Manufacturing'}. Replaces the stored field set."},"unapprove_if_approved":{"type":"boolean","title":"Unapprove If Approved","description":"Approved profiles are immutable by design. Set true to explicitly unlock and overwrite a human-approved profile. Left false, an approved profile returns 409 instead of being silently unapproved.","default":false}},"type":"object","required":["website_url","fields"],"title":"CompanyProfileUpdateRequest"},"CompanyResponse":{"properties":{"id":{"type":"integer","title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain"},"website":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Website"},"logo_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Logo Url"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone"},"address":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Address"},"city":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"City"},"state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"State"},"country":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country"},"zip":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Zip"},"founded_year":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Founded Year"},"employee_count":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Employee Count"},"revenue":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Revenue"},"industry":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Industry"},"industry_group":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Industry Group"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url"},"linkedin_followers":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Followers"},"facebook_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Facebook Url"},"twitter_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Twitter Url"},"crunchbase_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Crunchbase Url"},"meta_data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Meta Data"},"contact_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Contact Count"},"custom_fields":{"anyOf":[{"additionalProperties":{"anyOf":[{"type":"string"},{"type":"null"}]},"type":"object"},{"type":"null"}],"title":"Custom Fields"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["id"],"title":"CompanyResponse"},"CompanyTaskCreateRequest":{"properties":{"title":{"type":"string","title":"Title","description":"Task title."},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Task body."},"due_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Due Date","description":"ISO-8601 due date."},"assignee_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Assignee Id","description":"Assignee user id."},"assignee_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Assignee Name","description":"Assignee display name."},"priority":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Priority","description":"Priority, higher is more urgent."},"task_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Task Type","description":"Task type, e.g. `call`."},"tags":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":20},{"type":"null"}],"title":"Tags","description":"Up to 20 labels."}},"type":"object","required":["title"],"title":"CompanyTaskCreateRequest","description":"Mirrors `companies.interfaces.fastapi.router.CompanyTaskCreateRequest`."},"CompanyUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain"},"website":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Website"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone"},"address":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Address"},"city":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"City"},"state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"State"},"country":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country"},"zip":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Zip"},"industry":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Industry"},"employee_count":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Employee Count"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url"}},"type":"object","title":"CompanyUpdateRequest","description":"Request body for updating a company. All fields optional (partial update)."},"CompanyWorkflowType":{"type":"string","enum":["company_intelligence","stakeholder_mapping","deal_strategy","competitive_positioning"],"title":"CompanyWorkflowType","description":"Types of workflows that can be run on a company"},"ComplianceCertification":{"properties":{"enabled":{"type":"boolean","title":"Enabled","description":"Whether the organization holds this certification.","default":false},"achieved_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Achieved Date","description":"Date the certification was achieved (YYYY-MM-DD)."},"report_doc_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Report Doc Id","description":"Library document id for the uploaded report or certificate."}},"type":"object","title":"ComplianceCertification","description":"Mirrors `campaign_builder.routers.org_settings.CertificationStatus`."},"ComplianceSettingsUpdateRequest":{"properties":{"certifications":{"additionalProperties":{"$ref":"#/components/schemas/ComplianceCertification"},"type":"object","title":"Certifications","description":"Certification id -> status. Unknown ids are ignored by the server."}},"type":"object","required":["certifications"],"title":"ComplianceSettingsUpdateRequest","description":"Mirrors `UpdateComplianceSettingsRequest`.\n\nA PARTIAL patch keyed by certification id: only the ids you send are\ntouched, and an id the product does not support is ignored rather than\nrejected - which is the app's behaviour, not a choice made here. Read\n`GET /org/settings/compliance` for the supported ids."},"ComputedFieldState":{"properties":{"status":{"type":"string","enum":["recalculating","error","needs_input"],"title":"Status"},"code":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Code","description":"`error`: the failure code; `needs_input`: `needs_input`. Never the value or the input."},"needs":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Needs","description":"`needs_input` only: slug of the blank input (a field, or the relationship of an empty rollup). The value is empty."},"last_good_value":{"title":"Last Good Value","description":"`error` only: the value still stored from the last successful calculation (null when there is none). The grid shows only the chip; the record page shows this value next to it."},"computed_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Computed At","description":"When the value now stored came into being (the time it last CHANGED; a recalculation that confirmed it writes nothing). Null when nothing is stored. A `recalculating` cell shows that value, dimmed."},"failed_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Failed At","description":"`error` only: when the failure was recorded."}},"type":"object","required":["status"],"title":"ComputedFieldState","description":"Why a computed field of a record is not simply fresh. A field with no entry is fresh."},"ComputedStateRequest":{"properties":{"record_ids":{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":500,"minItems":1,"title":"Record Ids"}},"additionalProperties":false,"type":"object","required":["record_ids"],"title":"ComputedStateRequest"},"ComputedStateResponse":{"properties":{"states":{"additionalProperties":{"additionalProperties":{"$ref":"#/components/schemas/ComputedFieldState"},"type":"object"},"type":"object","title":"States"},"backfilling":{"items":{"type":"string"},"type":"array","title":"Backfilling"}},"type":"object","required":["states"],"title":"ComputedStateResponse"},"ComputedStatusResponse":{"properties":{"backfilling":{"type":"boolean","title":"Backfilling","description":"A job is walking every record of the object to (re)compute this field."},"pending_jobs":{"type":"integer","title":"Pending Jobs","description":"Unfinished recompute jobs for this field (a backfill counts as one)."},"failed":{"type":"boolean","title":"Failed","description":"Some record holds a calculation error, or a backfill was abandoned after its retries."},"failed_code":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Failed Code","description":"The most common error code among the failed records."},"failed_records":{"type":"integer","title":"Failed Records","description":"How many records hold an error for this field (the neutral `needs_input` is not one).","default":0},"last_completed_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Last Completed At","description":"When a backfill of this field last ran to the end; null before the first."}},"type":"object","required":["backfilling","pending_jobs","failed"],"title":"ComputedStatusResponse","description":"Where one computed field stands across all of its records (no record id needed)."},"ConceptsRequest":{"properties":{"brief":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Brief"},"count":{"type":"integer","maximum":6.0,"minimum":3.0,"title":"Count","default":4}},"type":"object","title":"ConceptsRequest","description":"Cheap creative directions to react to BEFORE generating. SPENDS CREDIT.\n\nOne LLM call for 3-6 directions, which is the point: it is far cheaper\nthan generating that many creatives and throwing five away."},"ConditionDto":{"properties":{"field":{"type":"string","title":"Field"},"operator":{"type":"string","title":"Operator"},"value":{"title":"Value"},"value_to":{"title":"Value To"}},"type":"object","required":["field","operator"],"title":"ConditionDto","description":"One routing condition."},"ConfigureFindPeopleRequest":{"properties":{"name":{"type":"string","title":"Name"},"list_id":{"type":"integer","title":"List Id","description":"Source COMPANY list."},"search_filters":{"items":{"$ref":"#/components/schemas/SearchFilterDto"},"type":"array","title":"Search Filters"},"column_mappings":{"anyOf":[{"items":{"$ref":"#/components/schemas/ColumnMappingDto"},"type":"array"},{"type":"null"}],"title":"Column Mappings"},"company_identifier_column":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Identifier Column"},"max_people_per_company":{"type":"integer","maximum":50.0,"minimum":1.0,"title":"Max People Per Company","default":5},"max_total_people":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Max Total People"},"destination_list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Destination List Id"},"create_new_list":{"type":"boolean","title":"Create New List","default":false},"new_list_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"New List Name"},"skip_existing_in_destination":{"type":"boolean","title":"Skip Existing In Destination","default":false},"skip_across_companies":{"type":"boolean","title":"Skip Across Companies","default":false},"auto_import":{"type":"boolean","title":"Auto Import","description":"Import results as soon as they are found, with no review step. This is what turns a saved configuration into an immediate run.","default":false}},"type":"object","required":["name","list_id"],"title":"ConfigureFindPeopleRequest","description":"Set up a people search across a company list."},"ConfigureRawSourceRequest":{"properties":{"source_type":{"type":"string","enum":["webhook","legacy_webhook","scraper_bot"],"title":"Source Type","description":"Which kind of source feeds this column.","default":"webhook"},"label":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Label"},"config":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Config","description":"Source-specific settings."},"rotate_existing":{"type":"boolean","title":"Rotate Existing","description":"Explicitly acknowledge that an existing credential is invalidated IMMEDIATELY. Anything already posting with the old key stops.","default":false},"expires_in_days":{"type":"integer","maximum":365.0,"minimum":1.0,"title":"Expires In Days","description":"Credential lifetime, applied when one is first generated.","default":90}},"type":"object","title":"ConfigureRawSourceRequest","description":"Bind an ingest source to a column."},"ConfigureStagingFindPeopleRequest":{"properties":{"name":{"type":"string","maxLength":255,"minLength":1,"title":"Name","default":"Find People"},"domain_column":{"type":"string","minLength":1,"title":"Domain Column","description":"Column holding company domains or LinkedIn URLs."},"lookup_field":{"type":"string","enum":["COMPANY_DOMAIN","COMPANY_LINKEDIN_URL"],"title":"Lookup Field","default":"COMPANY_DOMAIN"},"search_filters":{"items":{"$ref":"#/components/schemas/FindPeopleSearchFilter"},"type":"array","title":"Search Filters"},"broad_search_acknowledged":{"type":"boolean","title":"Broad Search Acknowledged","description":"Confirm an EMPTY filter set is intentional. An unfiltered search returns the widest - and most expensive - possible result.","default":false},"max_people_per_company":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Max People Per Company","default":5},"max_total_people":{"type":"integer","maximum":10000.0,"minimum":1.0,"title":"Max Total People","description":"Hard ceiling across every company row.","default":250},"destination_table_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Destination Table Id"},"create_destination_table":{"type":"boolean","title":"Create Destination Table","default":false},"destination_table_name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Destination Table Name"},"auto_create_columns":{"type":"boolean","title":"Auto Create Columns","default":true},"skip_existing":{"type":"boolean","title":"Skip Existing","default":true},"company_name_column":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Name Column"}},"type":"object","required":["domain_column"],"title":"ConfigureStagingFindPeopleRequest","description":"Search for contacts at each company row in a workbench table."},"ConfirmBookingRequest":{"properties":{"confirmed":{"type":"boolean","title":"Confirmed"},"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason"}},"type":"object","required":["confirmed"],"title":"ConfirmBookingRequest"},"ConfirmMigrationRequest":{"properties":{"field_mappings_override":{"anyOf":[{"additionalProperties":{"items":{"additionalProperties":true,"type":"object"},"type":"array"},"type":"object"},{"type":"null"}],"title":"Field Mappings Override","description":"Per entity type, the mappings to use instead of the discovered ones. Omit to accept what discovery proposed."},"selected_list_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Selected List Ids","description":"Import only these CRM lists. Omit to take every discovered list."},"owner_decisions":{"anyOf":[{"items":{"$ref":"#/components/schemas/MigrationOwnerDecision"},"type":"array","maxItems":500},{"type":"null"}],"title":"Owner Decisions","description":"Salesforce only: one decision per record owner who is not a graph8 member (at most 500). Required for every owner whose `match.status` is `unmatched`; optional `assign` for a `placeholder` owner. `match` moves every record the owner has; `assign` moves only their open deals and open tasks."}},"type":"object","title":"ConfirmMigrationRequest","description":"Accept a discovery and START IMPORTING.\n\nThis is the irreversible half: records begin landing in graph8 and a\nmigration cannot be un-run, only cancelled part-way.\n\nEvery field is OPTIONAL and omitting them accepts the discovery as\nproposed - which is the point of previewing it first. Send\n`field_mappings_override` to change where a CRM field lands,\n`selected_list_ids` to import only some lists, or `owner_decisions` to say\nwhat happens to the records of Salesforce owners who are not in graph8.\nA Salesforce discovery with an `unmatched` owner needs a decision for that\nowner: without one the confirm is refused with 422."},"ConnectRepoRequest":{"properties":{"repo_url":{"type":"string","title":"Repo Url","description":"Repository URL (e.g., https://github.com/org/repo)"},"repo_name":{"type":"string","title":"Repo Name","description":"Repository name (e.g., my-saas-app)"},"provider":{"type":"string","title":"Provider","description":"Repository provider: github, gitlab, local","default":"github"},"default_branch":{"type":"string","title":"Default Branch","description":"Default branch name","default":"main"}},"type":"object","required":["repo_url","repo_name"],"title":"ConnectRepoRequest"},"ConnectedCalendarResponse":{"properties":{"credential_id":{"type":"integer","title":"Credential Id"},"provider":{"type":"string","title":"Provider"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"},"is_valid":{"type":"boolean","title":"Is Valid","default":true},"invalid":{"type":"boolean","title":"Invalid","default":false},"sub_calendars":{"items":{"$ref":"#/components/schemas/SubCalendarResponse"},"type":"array","title":"Sub Calendars"}},"type":"object","required":["credential_id","provider"],"title":"ConnectedCalendarResponse"},"ConnectedConferencingResponse":{"properties":{"provider":{"type":"string","title":"Provider"},"name":{"type":"string","title":"Name"},"is_default":{"type":"boolean","title":"Is Default","default":false},"credential_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Credential Id"},"link":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Link"}},"type":"object","required":["provider","name"],"title":"ConnectedConferencingResponse"},"ConnectionListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"ConnectionListPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape."},"ConnectionPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"ConnectionPayload","description":"An open envelope for a connection, a token or a migration report.\n\nOpen because the migration STATUS payload carries a per-entity progress\nmap, a discovered-field map and a pipeline list that all grow with the\nproviders - and because a dropped warning on a migration report reads as\n\"nothing went wrong\"."},"ContactAssertRequest":{"properties":{"list_id":{"type":"integer","title":"List Id","description":"Target list ID"},"work_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Work Email","description":"Work email (primary match key)"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url","description":"LinkedIn URL (fallback match key)"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"personal_emails":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Personal Emails"},"direct_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Direct Phone"},"mobile_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mobile Phone"},"job_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Title"},"job_department":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Department"},"seniority_level":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Seniority Level"},"city":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"City"},"state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"State"},"country":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country"},"company_domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Domain"},"custom_fields":{"anyOf":[{"additionalProperties":{"anyOf":[{"type":"string"},{"type":"null"}]},"type":"object"},{"type":"null"}],"title":"Custom Fields","description":"Custom column values to write on this record, keyed by the column's display title (e.g. 'Followup 1'), its slug (e.g. 'udo_followup_1_ab12cd34'), or a case/space variant of the title. Keys that match no existing column are reported back in `ignored_fields` unless `create_missing_fields` is true."},"create_missing_fields":{"type":"boolean","title":"Create Missing Fields","description":"When true, any key in `custom_fields` that matches no existing column is created as a NEW list-scoped custom column (max 100 per request) and then written. Default false preserves the previous behaviour of not creating columns implicitly.","default":false}},"type":"object","required":["list_id"],"title":"ContactAssertRequest"},"ContactAssertResponse":{"properties":{"action":{"type":"string","title":"Action","description":"'created' or 'updated'"},"count":{"type":"integer","title":"Count","default":1},"custom_fields":{"$ref":"#/components/schemas/CustomFieldWriteReport"},"warnings":{"items":{"type":"string"},"type":"array","title":"Warnings","description":"Advisory notes about values saved as sent that look wrong (e.g. an unrecognised seniority or country). Empty when the input is clean."}},"type":"object","required":["action"],"title":"ContactAssertResponse"},"ContactBrief":{"properties":{"id":{"type":"integer","title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Role"}},"type":"object","required":["id"],"title":"ContactBrief","description":"Lightweight contact summary embedded in deal responses.\n\n`id` is the canonical `mashup_contact_id` (BigInt), matching how contacts\nare addressed everywhere else in the public API (g8_search_contacts,\ng8_lookup_person, etc.). `role` is the contact's role within THIS deal\n(champion / decision_maker / influencer / blocker / coach / end_user) and\nis null when no role was set."},"ContactBulkGetItem":{"properties":{"contact_id":{"type":"integer","title":"Contact Id"},"found":{"type":"boolean","title":"Found","description":"False when the contact does not exist or is outside this key's scope (indistinguishable on purpose, like the per-contact 404)."},"contact":{"anyOf":[{"$ref":"#/components/schemas/ContactResponse"},{"type":"null"}],"description":"The same record `GET /contacts/{contact_id}` returns. Null when not found."}},"type":"object","required":["contact_id","found"],"title":"ContactBulkGetItem","description":"One contact: the full record, or `found: false`."},"ContactBulkGetRequest":{"properties":{"contact_ids":{"items":{"type":"integer"},"type":"array","maxItems":100,"minItems":1,"title":"Contact Ids","description":"Up to 100 contact ids, the ids `GET /contacts` returns. Duplicates are read once; the response keeps first-seen order."},"include_custom_fields":{"type":"boolean","title":"Include Custom Fields","description":"When true, each found contact includes a `custom_fields` object keyed by column slug, as `GET /contacts/{contact_id}?include_custom_fields=true` does.","default":false}},"additionalProperties":false,"type":"object","required":["contact_ids"],"title":"ContactBulkGetRequest","description":"Which contacts to read in full."},"ContactBulkGetResponse":{"properties":{"items":{"items":{"$ref":"#/components/schemas/ContactBulkGetItem"},"type":"array","title":"Items"}},"type":"object","title":"ContactBulkGetResponse"},"ContactCaptureRule":{"properties":{"enabled":{"type":"boolean","title":"Enabled","default":true},"min_followers":{"type":"integer","minimum":0.0,"title":"Min Followers","default":0},"only_when_classified":{"type":"boolean","title":"Only When Classified","default":false}},"type":"object","title":"ContactCaptureRule","description":"When a matched post's author becomes a graph8 contact."},"ContactCompanySummary":{"properties":{"id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain"},"website":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Website"},"industry":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Industry"},"employee_count":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Employee Count"},"city":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"City"},"state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"State"},"country":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url"},"logo_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Logo Url"}},"type":"object","title":"ContactCompanySummary"},"ContactCreateRequest":{"properties":{"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id","description":"Optional target list ID. When provided, the contact is added to this list after it is created; omit to create the contact without a list."},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name","description":"Contact first name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name","description":"Contact last name"},"work_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Work Email","description":"Work email address"},"personal_emails":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Personal Emails","description":"Personal email addresses"},"direct_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Direct Phone","description":"Direct phone number"},"mobile_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mobile Phone","description":"Mobile phone number"},"job_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Title","description":"Job title"},"job_department":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Department","description":"Department"},"seniority_level":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Seniority Level","description":"Seniority level"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url","description":"LinkedIn profile URL"},"city":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"City","description":"City"},"state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"State","description":"State/Province"},"country":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country","description":"Country"},"company_domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Domain","description":"Company domain for matching"},"company_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Company Id","description":"Existing company id (mashup_companies.id) to attach"},"custom_fields":{"anyOf":[{"additionalProperties":{"anyOf":[{"type":"string"},{"type":"null"}]},"type":"object"},{"type":"null"}],"title":"Custom Fields","description":"Custom column values keyed by the column's display title (e.g. 'Followup 1'), its slug (e.g. 'udo_followup_1_ab12cd34'), or a case/space variant of the title. Keys matching no existing column are reported in the response's `custom_fields.ignored` unless `create_missing_fields` is true."},"create_missing_fields":{"type":"boolean","title":"Create Missing Fields","description":"When true, custom_fields keys that match no existing column are created as NEW custom columns (list-scoped when list_id is set) and then written.","default":false}},"type":"object","title":"ContactCreateRequest","description":"Request body for creating contacts."},"ContactCreateResponse":{"properties":{"status":{"type":"string","title":"Status"},"count":{"type":"integer","title":"Count"},"validation_errors":{"items":{"type":"string"},"type":"array","title":"Validation Errors"},"contact_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Contact Id"},"merged":{"type":"boolean","title":"Merged","default":false},"company_attached":{"type":"boolean","title":"Company Attached","default":false},"custom_fields":{"$ref":"#/components/schemas/CustomFieldWriteReport"},"warnings":{"items":{"type":"string"},"type":"array","title":"Warnings","description":"Advisory notes about values saved as sent that look wrong (e.g. an unrecognised seniority or country). Empty when the input is clean."}},"type":"object","required":["status","count"],"title":"ContactCreateResponse"},"ContactDealResponse":{"properties":{"deal_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Deal Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"stage":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage"},"value":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Value"},"currency":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Currency"},"role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Role"},"pipeline_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Pipeline Id"},"close_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Close Date"},"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"}},"type":"object","title":"ContactDealResponse","description":"Deal response from contact or company deals handler (dict-based)."},"ContactDocumentUpdateRequest":{"properties":{"content":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Content","description":"Replacement document body."},"structured_data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Structured Data","description":"Replacement structured payload."}},"type":"object","title":"ContactDocumentUpdateRequest","description":"Mirrors `campaign_builder.models.contact_documents.UpdateContactDocumentRequest`."},"ContactHistoryDTO":{"properties":{"contact_id":{"type":"integer","title":"Contact Id"},"responses":{"items":{"$ref":"#/components/schemas/ContactHistoryItemDTO"},"type":"array","title":"Responses"}},"type":"object","required":["contact_id","responses"],"title":"ContactHistoryDTO"},"ContactHistoryItemDTO":{"properties":{"survey_id":{"type":"string","title":"Survey Id"},"survey_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Survey Name"},"type":{"type":"string","title":"Type"},"score":{"type":"integer","title":"Score"},"classification":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Classification"},"channel":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Channel"},"responded_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Responded At"}},"type":"object","required":["survey_id","type","score"],"title":"ContactHistoryItemDTO"},"ContactListItem":{"properties":{"id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Id"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"work_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Work Email"},"direct_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Direct Phone"},"mobile_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mobile Phone"},"job_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Title"},"job_department":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Department"},"seniority_level":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Seniority Level"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url"},"city":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"City"},"state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"State"},"country":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country"},"company_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Company Id"},"company_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Name"},"company_domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Domain"},"company_website":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Website"},"company_industry":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Industry"},"company_employee_count":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Employee Count"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"},"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id"},"owner_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Name"},"custom_fields":{"anyOf":[{"additionalProperties":{"anyOf":[{"type":"string"},{"type":"null"}]},"type":"object"},{"type":"null"}],"title":"Custom Fields"}},"type":"object","title":"ContactListItem","description":"Lighter contact representation for list endpoints."},"ContactRelatedBatchRequest":{"properties":{"contact_ids":{"items":{"type":"integer"},"type":"array","maxItems":100,"minItems":1,"title":"Contact Ids","description":"Up to 100 contact ids, the same ids the per-contact routes take. Duplicates are read once; the response keeps first-seen order."},"include":{"items":{"type":"string","enum":["sequences","lists"]},"type":"array","minItems":1,"title":"Include","description":"Related records to return per contact. `sequences` matches `GET /contacts/{contact_id}/sequences`; `lists` matches `GET /contacts/{contact_id}/lists` (keyed on the contact primary key)."}},"additionalProperties":false,"type":"object","required":["contact_ids"],"title":"ContactRelatedBatchRequest","description":"Which contacts, and which of their related records, to read in one call."},"ContactRelatedBatchResponse":{"properties":{"items":{"items":{"$ref":"#/components/schemas/ContactRelatedItem"},"type":"array","title":"Items"}},"type":"object","title":"ContactRelatedBatchResponse"},"ContactRelatedItem":{"properties":{"contact_id":{"type":"integer","title":"Contact Id"},"found":{"type":"boolean","title":"Found","description":"False when the contact does not exist or is outside this key's scope (indistinguishable on purpose, like the per-contact 404)."},"sequences":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Sequences"},"lists":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Lists"}},"type":"object","required":["contact_id","found"],"title":"ContactRelatedItem","description":"One contact's related records. A field is present only when requested."},"ContactResponse":{"properties":{"id":{"type":"integer","title":"Id"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"full_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Full Name"},"work_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Work Email"},"personal_emails":{"anyOf":[{},{"type":"null"}],"title":"Personal Emails"},"direct_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Direct Phone"},"mobile_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mobile Phone"},"job_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Title"},"job_department":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Department"},"seniority_level":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Seniority Level"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url"},"twitter_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Twitter Url"},"facebook_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Facebook Url"},"city":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"City"},"state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"State"},"country":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country"},"about":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"About"},"confidence_score":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Confidence Score"},"company":{"anyOf":[{"$ref":"#/components/schemas/ContactCompanySummary"},{"type":"null"}]},"meta_data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Meta Data"},"custom_fields":{"anyOf":[{"additionalProperties":{"anyOf":[{"type":"string"},{"type":"null"}]},"type":"object"},{"type":"null"}],"title":"Custom Fields"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["id"],"title":"ContactResponse"},"ContactSupportRequest":{"properties":{"message":{"type":"string","maxLength":5000,"minLength":3,"title":"Message","description":"What the user needs help with, in their own words."},"contact_email":{"anyOf":[{"type":"string","format":"email"},{"type":"null"}],"title":"Contact Email","description":"Where graph8 support should reply. Optional for personal API keys (the key's own user email is used); REQUIRED for org-scoped machine keys, which carry no personal email."},"urgency":{"anyOf":[{"type":"string","maxLength":32},{"type":"null"}],"title":"Urgency","description":"Free-form urgency hint, e.g. 'normal', 'high', 'urgent'."}},"type":"object","required":["message"],"title":"ContactSupportRequest","description":"A support request relayed from an AI client (or direct API caller).\n\n``urgency`` is deliberately a free-form string, not an enum — LLM callers\nproduce arbitrary phrasing and a 422 on vocabulary would block a user who\nis already asking for help. Urgent-flavored values (\"high\", \"urgent\",\n\"critical\", \"asap\") get a visible subject-line prefix; everything else is\npassed through as informational text."},"ContactSupportResponse":{"properties":{"status":{"type":"string","title":"Status"},"notified":{"type":"integer","title":"Notified","description":"Support staff notified on this call (0 on cooldown).","default":0},"reply_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reply Email","description":"Address graph8 support will reply to."},"note":{"type":"string","title":"Note","description":"Human-readable summary for the caller to relay to the user.","default":""}},"type":"object","required":["status"],"title":"ContactSupportResponse","description":"Acknowledgment for a support request.\n\n``status`` is ``received`` on first delivery and ``already_received`` when\nthe per-user cooldown swallowed a duplicate (still HTTP 200 — a retryable\nerror code would make LLM callers loop harder)."},"ContactTag":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"color":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Color"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"archived":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Archived"},"contact_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Contact Count","description":"Contacts currently carrying the tag."}},"additionalProperties":true,"type":"object","title":"ContactTag"},"ContactTagAssignRequest":{"properties":{"tag_ids":{"items":{"type":"string"},"type":"array","minItems":1,"title":"Tag Ids"},"contact_ids":{"items":{"type":"integer"},"type":"array","title":"Contact Ids","description":"Contacts to tag."}},"type":"object","required":["tag_ids"],"title":"ContactTagAssignRequest"},"ContactTagCreateRequest":{"properties":{"name":{"type":"string","maxLength":50,"minLength":1,"title":"Name"},"color":{"anyOf":[{"type":"string","pattern":"^#[0-9A-Fa-f]{6}$"},{"type":"null"}],"title":"Color","description":"Six-digit hex colour, e.g. `#4F46E5`."},"description":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Description"}},"type":"object","required":["name"],"title":"ContactTagCreateRequest"},"ContactTagListResponse":{"properties":{"tags":{"items":{"$ref":"#/components/schemas/ContactTag"},"type":"array","title":"Tags"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"ContactTagListResponse"},"ContactTagMergeRequest":{"properties":{"source_tag_ids":{"items":{"type":"string"},"type":"array","minItems":1,"title":"Source Tag Ids","description":"Tags to fold in. Removed on success."},"target_tag_id":{"type":"string","title":"Target Tag Id","description":"Tag that survives and absorbs the assignments."}},"type":"object","required":["source_tag_ids","target_tag_id"],"title":"ContactTagMergeRequest"},"ContactTagUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":50,"minLength":1},{"type":"null"}],"title":"Name"},"color":{"anyOf":[{"type":"string","pattern":"^#[0-9A-Fa-f]{6}$"},{"type":"null"}],"title":"Color"},"description":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Description"},"archived":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Archived","description":"Archive without deleting."}},"type":"object","title":"ContactTagUpdateRequest","description":"Every field is optional; omit one to leave it untouched."},"ContactTagWriteResult":{"properties":{},"additionalProperties":true,"type":"object","title":"ContactTagWriteResult","description":"Whatever the handler reports about a write - counts, ids, or both."},"ContactUpdateRequest":{"properties":{"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"work_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Work Email"},"direct_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Direct Phone"},"mobile_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mobile Phone"},"job_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Title"},"job_department":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Department"},"seniority_level":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Seniority Level"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url"},"city":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"City"},"state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"State"},"country":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country"},"company_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Company Id"},"company_domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Domain"}},"type":"object","title":"ContactUpdateRequest","description":"Request body for updating a contact. All fields optional (partial update)."},"ContainerLogResponse":{"properties":{"pod":{"type":"string","title":"Pod"},"container":{"type":"string","title":"Container"},"kind":{"type":"string","enum":["init","container"],"title":"Kind"},"text":{"type":"string","title":"Text"},"truncated":{"type":"boolean","title":"Truncated","description":"The tail hit the per-container byte cap. Earlier output exists and was not returned.","default":false}},"type":"object","required":["pod","container","kind","text"],"title":"ContainerLogResponse","description":"One container's tail of output.\n\nA build is five steps in one pod (fetch, scan-source, build, scan-image,\npush), so a single flat blob would leave a caller unable to say which step\nfailed. ``kind`` separates the four init steps from the one container, which\nis the ordering Kubernetes actually runs them in."},"ContentGridColumnRequest":{"properties":{"skill_id":{"type":"string","format":"uuid","title":"Skill Id","description":"The content skill this column runs."},"column_name":{"type":"string","title":"Column Name"},"input_mapping":{"anyOf":[{"additionalProperties":{"type":"string"},"type":"object"},{"type":"null"}],"title":"Input Mapping","description":"Skill input name -> row field it reads, e.g. `{\"keyword\": \"target_keyword\"}`."}},"type":"object","required":["skill_id","column_name"],"title":"ContentGridColumnRequest"},"ContentGridRunRequest":{"properties":{"row_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Row Ids","description":"Only these rows. Omit for every row."}},"type":"object","title":"ContentGridRunRequest"},"ContentGridSkillPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"ContentGridSkillPayload","description":"A grid column, a queued run, or a run's result."},"ContentSourceItem":{"properties":{"type":{"type":"string","enum":["website","blog","docs","developers","linkedin","reddit","twitter"],"title":"Type","description":"`website`/`blog`/`docs`/`developers` are properties you OWN; `linkedin`/`reddit`/`twitter` are external channels."},"url":{"type":"string","title":"Url","description":"Full URL - the site URL for an owned property, the profile URL for an external channel."},"primary":{"type":"boolean","title":"Primary","description":"Owned types only. The single primary website, mirrored to the org's `primary_website_url`. At most one source may set it.","default":false}},"additionalProperties":false,"type":"object","required":["type","url"],"title":"ContentSourceItem","description":"Mirrors `campaign_builder.routers.org_settings.ContentSourceItem`.\n\n`extra=\"forbid\"` matches the app: a typo'd key on a content source is a\nsilently ignored instruction otherwise, and the list is REPLACED wholesale\non every write, so a dropped key is a dropped source."},"ContentSourcesUpdateRequest":{"properties":{"sources":{"items":{"$ref":"#/components/schemas/ContentSourceItem"},"type":"array","title":"Sources","description":"The complete set of content sources. Anything omitted is deleted."}},"additionalProperties":false,"type":"object","required":["sources"],"title":"ContentSourcesUpdateRequest","description":"Mirrors `UpdateContentSourcesRequest`.\n\nREPLACES the whole list. There is no partial update: send every source you\nwant to keep, or it is removed."},"ContentWorkspaceCrawlRequest":{"properties":{"start_url":{"type":"string","title":"Start Url","description":"Must be on the org's registered website."},"include_paths":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Include Paths","description":"e.g. ['/blog', '/resources']."},"exclude_paths":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Exclude Paths","description":"e.g. ['/author', '/tag']."},"max_pages":{"type":"integer","maximum":5000.0,"minimum":1.0,"title":"Max Pages","description":"The ceiling on pages crawled - and on the spend.","default":500}},"type":"object","required":["start_url"],"title":"ContentWorkspaceCrawlRequest","description":"Deep-crawl the org's OWN website. SPENDS PROVIDER CREDIT, per page crawled."},"ContentWorkspacePageUpdateRequest":{"properties":{"primary_topic":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Primary Topic"},"intent":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Intent"},"page_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Page Type"},"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id"},"refresh_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Refresh Status"},"refresh_scope":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Refresh Scope"},"primary_keyword":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Primary Keyword"},"key_issues":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Key Issues"},"planned_changes":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Planned Changes"}},"type":"object","title":"ContentWorkspacePageUpdateRequest","description":"Partial update of a page's SEO-refresh planning fields."},"ContentWorkspaceSitemapImportRequest":{"properties":{"sitemap_url":{"type":"string","title":"Sitemap Url"},"include_patterns":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Include Patterns","description":"Glob patterns to include."},"exclude_patterns":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Exclude Patterns","description":"Glob patterns to exclude."},"max_pages":{"type":"integer","maximum":5000.0,"minimum":1.0,"title":"Max Pages","default":500}},"type":"object","required":["sitemap_url"],"title":"ContentWorkspaceSitemapImportRequest","description":"Import the pages listed in an XML sitemap."},"ContinueVideoClipRequest":{"properties":{"prompt_inputs":{"$ref":"#/components/schemas/VideoClipPromptInputs"},"prompt_final":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Prompt Final"},"duration_seconds":{"type":"integer","enum":[4,6,8],"title":"Duration Seconds","default":8}},"type":"object","required":["prompt_inputs"],"title":"ContinueVideoClipRequest","description":"Generate the NEXT shot, starting from this clip's last frame. SPENDS CREDIT."},"ConversationStateRequest":{"properties":{"starred":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Starred"},"archived":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Archived"},"spam":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Spam"}},"type":"object","title":"ConversationStateRequest","description":"Star / archive / spam, from the CALLER's side of the thread only.\n\nEach flag is explicit rather than a toggle, so a retried request is\nidempotent instead of flipping the state back. Omitted flags are untouched."},"CopilotCanvasContext":{"properties":{"activeDocument":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Activedocument","description":"{path, content, type, status}."},"selection":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Selection","description":"{text, start_line, end_line}."},"cursor":{"anyOf":[{"additionalProperties":{"type":"integer"},"type":"object"},{"type":"null"}],"title":"Cursor","description":"{line, column}."},"mode":{"type":"string","enum":["global","campaign","account"],"title":"Mode","default":"global"},"campaignId":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaignid"},"accountId":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Accountid"}},"type":"object","title":"CopilotCanvasContext","description":"What the copilot is looking at: a document, a selection, a campaign or account."},"CopilotChatMessage":{"properties":{"role":{"type":"string","enum":["user","assistant","system","tool"],"title":"Role"},"content":{"type":"string","title":"Content"},"tool_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Tool Name"},"tool_result":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Tool Result"}},"type":"object","required":["role","content"],"title":"CopilotChatMessage","description":"One earlier turn of the conversation."},"CopilotChatRequest":{"properties":{"message":{"type":"string","minLength":1,"title":"Message"},"canvas_context":{"anyOf":[{"$ref":"#/components/schemas/CopilotCanvasContext"},{"type":"null"}]},"conversation_history":{"anyOf":[{"items":{"$ref":"#/components/schemas/CopilotChatMessage"},"type":"array"},{"type":"null"}],"title":"Conversation History"},"mentions":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Mentions","description":"Results from `POST /copilot/mention-search`."},"session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Id"},"web_search":{"type":"boolean","title":"Web Search","description":"Search the web before answering.","default":false},"thinking":{"type":"boolean","title":"Thinking","description":"Extended thinking.","default":false},"research":{"type":"boolean","title":"Research","description":"Multi-step deep research. The most expensive option.","default":false}},"type":"object","required":["message"],"title":"CopilotChatRequest","description":"One message to the Studio copilot. SPENDS CREDIT. The answer is returned whole."},"CopilotContextLoadRequest":{"properties":{"keyword_id":{"type":"string","format":"uuid","title":"Keyword Id","description":"The buyer-intent keyword to open a conversation about."},"company_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Company Id","description":"Narrow the context to one company."},"contact_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Contact Id","description":"Narrow the context to one contact."}},"type":"object","required":["keyword_id"],"title":"CopilotContextLoadRequest","description":"Mirror of `load_intent_context.router.LoadIntentContextRequest`."},"CopilotLandingPageActionRequest":{"properties":{"action_type":{"type":"string","enum":["edit_section","add_section","remove_section","reorder_sections"],"title":"Action Type"},"landing_page_id":{"type":"string","title":"Landing Page Id"},"section_idx":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Section Idx","description":"For edit_section and remove_section."},"instruction":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Instruction","description":"For edit_section."},"selected_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Selected Text"},"new_section_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"New Section Type","description":"For add_section."},"new_order":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"New Order","description":"For reorder_sections: the new index order."}},"type":"object","required":["action_type","landing_page_id"],"title":"CopilotLandingPageActionRequest","description":"A section-level change to a landing page. `edit_section` SPENDS CREDIT."},"CopilotMemoryListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"CopilotMemoryListPayload","description":"An open envelope for a LIST answer, so a bare list keeps its shape."},"CopilotMemoryPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"CopilotMemoryPayload","description":"An open envelope for one memory, wiki or sharing answer.\n\nOpen because the personal wiki is a DOCUMENT whose sections follow what has\nbeen learned about a person, and because each fact carries provenance -\nwhich mailbox or meeting it came from - that grows as new sources are\nconnected. Pinning the shape would silently drop the provenance on the\nnewest source, and on a \"what do you know about me\" surface a fact with no\nvisible origin is worse than no fact."},"CopilotMentionSearchRequest":{"properties":{"query":{"type":"string","title":"Query","default":""},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id"},"mode":{"anyOf":[{"type":"string","enum":["global","campaign","account"]},{"type":"null"}],"title":"Mode"}},"type":"object","title":"CopilotMentionSearchRequest","description":"Find documents, personas, ICPs, campaigns and teammates to @mention."},"CorrespondenceCreateRequest":{"properties":{"channel":{"type":"string","title":"Channel","description":"`email`, `linkedin` or `call_notes`."},"direction":{"type":"string","title":"Direction","description":"`inbound` or `outbound`."},"subject":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subject"},"content":{"type":"string","title":"Content","description":"The body. Indexed for retrieval."},"correspondence_date":{"type":"string","format":"date-time","title":"Correspondence Date","description":"When it happened - NOT when it was recorded. Required."},"stakeholder_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stakeholder Id","description":"The person at the account, when known."},"external_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"External Id","description":"Your id for this message. The app uses it to skip duplicates on `/correspondence/import`, so send it to make an import re-runnable."}},"type":"object","required":["channel","direction","content","correspondence_date"],"title":"CorrespondenceCreateRequest","description":"One piece of correspondence with an account.\n\nMirrors `campaign_builder.routers.correspondence.CorrespondenceCreate`.\n\n`channel` and `direction` are NOT closed here, because the app does not\nclose them either: it stores whatever it is given. The values it reads\nelsewhere are `email` / `linkedin` / `call_notes` and `inbound` /\n`outbound`, and a value outside those is accepted and simply never matched\nby a filter."},"CorrespondenceImportRequest":{"properties":{"items":{"items":{"$ref":"#/components/schemas/CorrespondenceCreateRequest"},"type":"array","maxItems":500,"minItems":1,"title":"Items","description":"The records. Bounded at 500 by this contract - the app has no ceiling, and an unbounded body on a synchronous per-row insert is a request that times out halfway through having written some rows."}},"type":"object","required":["items"],"title":"CorrespondenceImportRequest","description":"Bulk import. Mirrors `correspondence.ImportCorrespondenceRequest`.\n\nPartial success is the normal outcome: the response reports `imported`,\n`skipped` and `errors` and the HTTP status stays 200, so read the body\nrather than the status."},"CoverageDTO":{"properties":{"responded":{"type":"integer","title":"Responded"},"total_contacts":{"type":"integer","title":"Total Contacts"},"rate":{"type":"number","title":"Rate"}},"type":"object","required":["responded","total_contacts","rate"],"title":"CoverageDTO"},"CreateAdCreativeRequest":{"properties":{"platform":{"type":"string","title":"Platform"},"ad_format":{"type":"string","title":"Ad Format"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"image_source":{"type":"string","title":"Image Source","description":"'ai' generates an image; 'library' reuses one.","default":"ai"},"library_image_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Library Image Id"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id"},"prompt":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Prompt"},"reference_image_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Reference Image Ids"}},"type":"object","required":["platform","ad_format"],"title":"CreateAdCreativeRequest","description":"Generate an ad creative. SPENDS CREDIT - copy and, by default, imagery.\n\n`image_source` 'ai' generates the image; 'library' takes\n`library_image_id` from the image library instead and is the cheaper of\nthe two."},"CreateAdCreativeSetRequest":{"properties":{"personas":{"items":{"$ref":"#/components/schemas/CampaignSetPersona"},"type":"array","maxItems":6,"minItems":1,"title":"Personas"},"platforms":{"items":{"type":"string"},"type":"array","maxItems":4,"minItems":1,"title":"Platforms"},"variants_per_cell":{"type":"integer","maximum":3.0,"minimum":1.0,"title":"Variants Per Cell","default":1},"brief":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Brief"},"formats":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Formats","description":"Platform -> ad_format override. Omit for each platform's default."},"image_source":{"type":"string","const":"ai","title":"Image Source","default":"ai"}},"type":"object","required":["personas","platforms"],"title":"CreateAdCreativeSetRequest","description":"Generate a persona x platform (x variant) matrix of creatives. SPENDS CREDIT.\n\nOne full creative per cell: `len(personas) * len(platforms) *\nvariants_per_cell`, capped at 24 per batch (a larger matrix is a 422).\nAI imagery only - `image_source` is fixed to `ai`."},"CreateAgentRunRequest":{"properties":{"agent_id":{"type":"string","title":"Agent Id","description":"Which agent drives the loop: 'onboarding', 'dialer_setup', 'sequencer_setup', 'campaign_run', 'voice_setup', 'marketplace', 'dev_setup', or a free-form value for an ad-hoc session."},"title":{"type":"string","maxLength":500,"minLength":1,"title":"Title"},"goal":{"type":"string","minLength":1,"title":"Goal","description":"Free text the planner works from."},"entry_point":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entry Point"},"visibility":{"type":"string","pattern":"^(shared|private)$","title":"Visibility","description":"'private' (default) keeps the run yours. 'shared' lets the organization see it, though only you can cancel it.","default":"private"},"subject_account_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subject Account Id","description":"Bind the run to a company."},"subject_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subject Campaign Id","description":"Bind the run to a campaign."},"session_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Title"},"seed_message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Seed Message","description":"An opening user turn, rendered as the first message."},"skill_mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Skill Mode","description":"'web_search' | 'deep_thinking' | 'research'. Unknown values are ignored."}},"type":"object","required":["agent_id","title","goal"],"title":"CreateAgentRunRequest","description":"Start a durable agent run. See the module docstring for what is omitted."},"CreateAgentSessionRequest":{"properties":{"approval_mode":{"type":"string","pattern":"^(review|auto_apply)$","title":"Approval Mode","description":"'review' (default) stages each patch for a human to approve in Studio. 'auto_apply' writes straight to the draft. Bound to the session at creation, so a later patch cannot escalate itself.","default":"review"}},"type":"object","title":"CreateAgentSessionRequest","description":"How the agent wants its edits handled once it starts patching."},"CreateAppPageRequest":{"properties":{"name":{"type":"string","title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"sources":{"items":{"$ref":"#/components/schemas/AppPageSourceDto"},"type":"array","minItems":1,"title":"Sources","description":"At least one. A page with no data source can never be generated."}},"type":"object","required":["name","sources"],"title":"CreateAppPageRequest"},"CreateAppRequest":{"properties":{"name":{"type":"string","maxLength":200,"minLength":1,"title":"Name"},"slug":{"type":"string","maxLength":100,"minLength":1,"pattern":"^[a-zA-Z0-9][a-zA-Z0-9_-]*$","title":"Slug","description":"Stable identifier, unique within your organization. Lowercased on write, so `CRM` and `crm` are the same app."},"registered_origins":{"items":{"type":"string"},"type":"array","maxItems":20,"title":"Registered Origins","description":"https-only origins a browser app token may be presented from. An http origin is rejected — a bearer token sent over http is a token disclosed to the network."}},"type":"object","required":["name","slug"],"title":"CreateAppRequest","description":"Mirrors `CreateAppInput`."},"CreateApprovalShareRequest":{"properties":{"content_type":{"type":"string","title":"Content Type"},"content_id":{"type":"string","title":"Content Id"},"expires_in_days":{"type":"integer","maximum":90.0,"minimum":1.0,"title":"Expires In Days","default":14}},"type":"object","required":["content_type","content_id"],"title":"CreateApprovalShareRequest","description":"Mint a tokenised approval link for a piece. Spends nothing.\n\nThe link is a BEARER URL: anyone holding it can approve or reject the\npiece without a graph8 login. That is the point - it goes to a client -\nbut it means the expiry is the only thing bounding it."},"CreateAutoEnrichmentConfigRequest":{"properties":{"audience_id":{"type":"integer","exclusiveMinimum":0.0,"title":"Audience Id","description":"The list."},"enrichment_type":{"type":"string","enum":["waterfall","ai"],"title":"Enrichment Type"},"column_id":{"type":"string","maxLength":255,"minLength":1,"title":"Column Id","description":"The waterfall column or AI group id."},"trigger_on_insert":{"type":"boolean","title":"Trigger On Insert","default":true}},"type":"object","required":["audience_id","enrichment_type","column_id"],"title":"CreateAutoEnrichmentConfigRequest","description":"Enrich every record that lands on a list. ARMS ONGOING SPEND."},"CreateBookingRequest":{"properties":{"event_type_id":{"type":"integer","title":"Event Type Id"},"start_time":{"type":"string","title":"Start Time"},"end_time":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"End Time"},"override_availability":{"type":"boolean","title":"Override Availability","default":false},"attendees":{"items":{"$ref":"#/components/schemas/AttendeeInput"},"type":"array","title":"Attendees"},"location":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Location"},"selected_location":{"anyOf":[{"$ref":"#/components/schemas/LocationItem"},{"type":"null"}]},"selected_conferencing":{"anyOf":[{"$ref":"#/components/schemas/LocationItem"},{"type":"null"}]},"responses":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Responses"},"guests":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Guests"},"metadata":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Metadata"},"recurring_event_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Recurring Event Id"},"language":{"type":"string","title":"Language","default":"en"},"slot_uid":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slot Uid"}},"type":"object","required":["event_type_id","start_time","attendees"],"title":"CreateBookingRequest"},"CreateCallRequest":{"properties":{"call_mode":{"type":"string","enum":["compete","assisted"],"title":"Call Mode","description":"`compete` is the rep alone against the AI prospect; `assisted` is the coached variant."},"prospect_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Prospect Name"},"prospect_company":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Prospect Company"},"persona_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Persona Type"}},"type":"object","required":["call_mode"],"title":"CreateCallRequest","description":"Start a practice call record.\n\n`call_mode` is CLOSED to the app's two values. The app validates it in a\nfield validator that raises inside the proxy rather than at the request\nboundary, so an open string here would be a 500 instead of a 422 naming\nboth modes."},"CreateCompanyColumnRequest":{"properties":{"title":{"type":"string","title":"Title","description":"Column title shown in the UI (e.g. 'Tier')"},"data_type":{"$ref":"#/components/schemas/ColumnType","description":"Column data type: 'text', 'int' (whole number), 'numeric' (decimal) or 'boolean' (yes/no). Other values 422.","default":"text"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id","description":"If set, the column is list-scoped (only visible on that list). Required when `enrichment` is supplied — waterfall pipelines are list-scoped."},"created_by":{"type":"string","format":"email","title":"Created By","description":"Email of the user creating the column (for audit)."},"enrichment":{"anyOf":[{"$ref":"#/components/schemas/CreateFieldEnrichmentInput"},{"type":"null"}],"description":"STRONGLY RECOMMENDED. Optional waterfall enrichment block. When supplied, a companion `enrichment_configs` row is created alongside the column so the UI 'Enrich' button works immediately. Without it the column exists but isn't enrichable until a pipeline is configured via POST /enrichment/waterfall/configs."}},"type":"object","required":["title","created_by"],"title":"CreateCompanyColumnRequest","description":"Request body for `POST /companies/columns/create`.\n\nMirrors the shared `CreateColumnRequest` shape (`title`, `data_type`,\n`list_id`, `created_by`) plus an OPTIONAL `enrichment` block that, when\nsupplied, provisions a companion waterfall pipeline in the same\nrequest — so the new column is immediately runnable via\n`POST /enrichment/waterfall/enrich`.\n\nWithout the `enrichment` block the column is created, but it has no\nenrichment plan; the UI \"Enrich\" button (and `g8_enrich_contacts` in\nwaterfall mode) will return 422 (`waterfall_config_missing`) until a\npipeline is provisioned separately via\n`POST /enrichment/waterfall/configs`.\n\nBackwards compatible: callers that previously POSTed only `title` /\n`data_type` / `list_id` / `created_by` continue to work unchanged."},"CreateCompanyColumnResponse":{"properties":{"id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Id"},"title":{"type":"string","title":"Title"},"data_type":{"$ref":"#/components/schemas/ColumnType","default":"text"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"object_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Object Id"},"is_global":{"type":"boolean","title":"Is Global","description":"Computed: True when object_id is null/empty (global column).","default":false},"enrichment":{"anyOf":[{"$ref":"#/components/schemas/CreateFieldEnrichmentResponse"},{"type":"null"}],"description":"Populated when the request included an `enrichment` block. Use `enrichment.column_id` for subsequent POST /enrichment/waterfall/enrich calls."},"already_existed":{"type":"boolean","title":"Already Existed","description":"True when a column with this name already existed in this scope, so the existing column was returned. A different `data_type` is rejected with 409.","default":false},"existing_data_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Existing Data Type","description":"When `already_existed` is true: the existing column's data type."},"warnings":{"items":{"type":"string"},"type":"array","title":"Warnings","description":"Non-blocking notices (e.g. a same-named org-wide column also shows on this list)."}},"type":"object","required":["title"],"title":"CreateCompanyColumnResponse","description":"Response shape for `POST /companies/columns/create`.\n\nMirrors the `Column` entity fields verbatim so existing callers reading\n`data.id` / `data.title` / `data.name` / `data.is_global` etc. keep\nworking without code changes. Adds one new optional `enrichment` field\nthat is populated when the request included an `enrichment` block."},"CreateCompetitorRequest":{"properties":{"domain":{"type":"string","maxLength":255,"minLength":1,"title":"Domain"},"name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Name"},"tier":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Tier","default":"tier2"},"scan_config":{"anyOf":[{"$ref":"#/components/schemas/ScanConfigDTO"},{"type":"null"}]},"scan_on_add":{"type":"boolean","title":"Scan On Add","default":false}},"type":"object","required":["domain"],"title":"CreateCompetitorRequest"},"CreateContactColumnRequest":{"properties":{"title":{"type":"string","title":"Title","description":"Column title shown in the UI (e.g. 'Lead Score')"},"data_type":{"$ref":"#/components/schemas/ColumnType","description":"Column data type: 'text', 'int' (whole number), 'numeric' (decimal) or 'boolean' (yes/no). Other values 422.","default":"text"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id","description":"If set, the column is list-scoped (only visible on that list). Required when `enrichment` is supplied — waterfall pipelines are list-scoped."},"created_by":{"type":"string","format":"email","title":"Created By","description":"Email of the user creating the column (for audit)."},"enrichment":{"anyOf":[{"$ref":"#/components/schemas/CreateFieldEnrichmentInput"},{"type":"null"}],"description":"STRONGLY RECOMMENDED. Optional waterfall enrichment block. When supplied, a companion `enrichment_configs` row is created alongside the column so the UI 'Enrich' button works immediately. Without it the column exists but isn't enrichable until a pipeline is configured via POST /enrichment/waterfall/configs."}},"type":"object","required":["title","created_by"],"title":"CreateContactColumnRequest","description":"Request body for `POST /contacts/columns/create`.\n\nMirrors the shared `CreateColumnRequest` shape (`title`, `data_type`,\n`list_id`, `created_by`) plus an OPTIONAL `enrichment` block that, when\nsupplied, provisions a companion waterfall pipeline in the same\nrequest — so the new column is immediately runnable via\n`POST /enrichment/waterfall/enrich`.\n\nWithout the `enrichment` block the column is created, but it has no\nenrichment plan; the UI \"Enrich\" button (and `g8_enrich_contacts` in\nwaterfall mode) will return 422 (`waterfall_config_missing`) until a\npipeline is provisioned separately via\n`POST /enrichment/waterfall/configs`.\n\nBackwards compatible: callers that previously POSTed only `title` /\n`data_type` / `list_id` / `created_by` continue to work unchanged."},"CreateContactColumnResponse":{"properties":{"id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Id"},"title":{"type":"string","title":"Title"},"data_type":{"$ref":"#/components/schemas/ColumnType","default":"text"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"object_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Object Id"},"is_global":{"type":"boolean","title":"Is Global","description":"Computed: True when object_id is null/empty (global column).","default":false},"enrichment":{"anyOf":[{"$ref":"#/components/schemas/CreateFieldEnrichmentResponse"},{"type":"null"}],"description":"Populated when the request included an `enrichment` block. Use `enrichment.column_id` for subsequent POST /enrichment/waterfall/enrich calls."},"already_existed":{"type":"boolean","title":"Already Existed","description":"True when a column with this name already existed in this scope, so the existing column was returned. A different `data_type` is rejected with 409.","default":false},"existing_data_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Existing Data Type","description":"When `already_existed` is true: the existing column's data type."},"warnings":{"items":{"type":"string"},"type":"array","title":"Warnings","description":"Non-blocking notices (e.g. a same-named org-wide column also shows on this list)."}},"type":"object","required":["title"],"title":"CreateContactColumnResponse","description":"Response shape for `POST /contacts/columns/create`.\n\nMirrors the `Column` entity fields verbatim so existing callers reading\n`data.id` / `data.title` / `data.name` / `data.is_global` etc. keep\nworking without code changes. Adds one new optional `enrichment` field\nthat is populated when the request included an `enrichment` block."},"CreateConversionActionRequest":{"properties":{"name":{"type":"string","maxLength":200,"title":"Name","default":"graph8 Landing Page Conversions"},"category":{"type":"string","title":"Category","default":"DEFAULT"},"primary_for_goal":{"type":"boolean","title":"Primary For Goal","default":true}},"type":"object","title":"CreateConversionActionRequest","description":"Request body for POST /audience-sync/google/conversion-actions.\n\nAll fields optional — an empty body provisions the default primary\n\"graph8 Landing Page Conversions\" action (category DEFAULT), matching what\nDemand Gen / PMax launches auto-provision."},"CreateCredentialRequest":{"properties":{"client_org_id":{"type":"string","title":"Client Org Id","description":"The client organization this credential acts for. It must already have a consented installation of the app — a credential is bound to one tenant and cannot be pointed at another later."}},"type":"object","required":["client_org_id"],"title":"CreateCredentialRequest","description":"A builder minting a service credential for one consented tenant."},"CreateDealColumnRequest":{"properties":{"title":{"type":"string","maxLength":100,"minLength":1,"title":"Title","description":"Display name."},"data_type":{"type":"string","enum":["text","int","numeric","number","boolean","date"],"title":"Data Type","description":"Closed to what the app accepts. It validates this inside the handler, so a free string would raise there and escape as a 500 instead of a 422 naming the valid types.","default":"text"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id","description":"Scope the column to one list. Null creates a GLOBAL column."}},"type":"object","required":["title"],"title":"CreateDealColumnRequest","description":"Add a custom column to the deals grid."},"CreateDefaultWaterfallConfigRequest":{"properties":{"list_id":{"type":"integer","title":"List Id","description":"List ID to attach the pipeline to"},"name":{"type":"string","title":"Name","description":"Human-readable name for the pipeline","default":"API Auto-Created Pipeline"},"field_to_enrich":{"type":"string","title":"Field To Enrich","description":"Target field identifier for this pipeline (legacy; ignored when `field` is set)","default":"work_email"},"field":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Field","description":"Canonical enrichment column to fill — CONTACT_DIRECT_PHONE, CONTACT_MOBILE_PHONE, CONTACT_WORK_EMAIL, CONTACT_PERSONAL_EMAILS, CONTACT_LINKEDIN_URL, COMPANY_PHONE, COMPANY_LINKEDIN_URL — or a friendly synonym ('phone', 'mobile', 'email', 'linkedin', 'company_phone'). When set, the pipeline is built from the server's per-field waterfall TEMPLATE, so each provider runs its CORRECT action for that column (e.g. leadmagic `mobile_finder` for a phone, not `email_finder`), and the enriched value is written into the real contact/company column — exactly like the web UI's 'enrich existing column' flow. Combine with `providers[]` to keep only those providers from the template (their correct per-field action is preserved). Mutually exclusive with `steps[]`. When omitted, the legacy bare/`providers[]` email-finder behavior is unchanged."},"skip_existing_values":{"type":"boolean","title":"Skip Existing Values","description":"If true, the pipeline skips contacts where the target field is already populated","default":true},"providers":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Providers","description":"Ordered list of provider names — server builds default email-finder steps in this order. Mutually exclusive with `steps`. Allowed providers: graph8, hunter, prospeo, dropcontact, icypeas, leadmagic, emaillistverify, apollo, lusha, rocketreach. Use `steps[]` for full control."},"steps":{"anyOf":[{"items":{"$ref":"#/components/schemas/WaterfallStepInput"},"type":"array"},{"type":"null"}],"title":"Steps","description":"Full caller-supplied step list (advanced). Persisted verbatim into the pipeline. Mutually exclusive with `providers`."},"email_verification":{"anyOf":[{"$ref":"#/components/schemas/EmailVerificationInput"},{"type":"null"}],"description":"Optional post-enrichment email verification config. When set, ZeroBounce/Hunter/Icypeas/LeadMagic runs after the main waterfall and writes verification status into the column."},"credential_mode":{"type":"string","enum":["auto","system","byok"],"title":"Credential Mode","description":"How to resolve each provider step's credential source. Applies to the `providers[]` shortcut and the bare default; `steps[]` payloads always honor their own per-step `is_system_provider`. 'auto' (default, matches the UI): for each provider use the org's BYOK key when one is configured (free), otherwise graph8's system key for funded providers (charges credits). 'system': force graph8 system keys for funded providers (charges credits). 'byok': force the org's own keys for every non-graph8 provider (legacy behavior — steps silently skip when no key exists). graph8 is always system-funded regardless of mode.","default":"auto"}},"type":"object","required":["list_id"],"title":"CreateDefaultWaterfallConfigRequest","description":"Create (or reuse) a waterfall pipeline for a list.\n\nThree call-styles, in increasing order of control:\n\n1. **Bare** — pass only `list_id`. Server builds a single-step graph8\n   lookup pipeline that fills name/email/company for 0 credits.\n   Backward-compatible with the pre-2026-06 contract.\n2. **By providers** — pass `providers=[\"hunter\",\"prospeo\"]`. Server maps\n   each provider to its default email-finder action (see provider matrix\n   in `docs/developer-api-reference.md`) and ordered steps. Use this when\n   you want a 1-line \"try these providers, in this order\" pipeline.\n3. **By steps** — pass `steps=[...]` with full step shapes. Server\n   persists them verbatim. Use this when you need provider-specific\n   config (e.g. apollo `reveal_phone_numbers=true`).\n\n`providers[]` and `steps[]` are mutually exclusive — pass one or\nneither, not both. `email_verification` may be combined with any\ncall-style; when set it runs after the main waterfall and follows the\nsame credit + valid-status rules the UI uses.\n\n`list_id` is required; everything else has a sensible default so callers\npass the minimum. `skip_existing_values` defaults True so we never\noverwrite populated fields. Idempotent by `(list_id, name)`."},"CreateDefaultWaterfallConfigResponse":{"properties":{"column_id":{"type":"string","title":"Column Id"},"config_id":{"type":"string","title":"Config Id"},"name":{"type":"string","title":"Name"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"created":{"type":"boolean","title":"Created","description":"True if a new config was created; False if an existing one with the same name was reused","default":false},"providers":{"items":{"type":"string"},"type":"array","title":"Providers","description":"Ordered, de-duplicated provider list of the persisted (or reused) pipeline."},"email_verification":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Email Verification","description":"Persisted email_verification block, if any. Mirrors EmailVerificationInput shape."},"providers_detail":{"items":{"$ref":"#/components/schemas/ProviderStepDetail"},"type":"array","title":"Providers Detail","description":"Per-step credential breakdown (system vs BYOK + readiness) for the persisted pipeline."},"missing_credentials":{"items":{"type":"string"},"type":"array","title":"Missing Credentials","description":"Providers whose step is BYOK but the org has no active key (these steps will be skipped at run time). Empty when every step is runnable."}},"type":"object","required":["column_id","config_id","name"],"title":"CreateDefaultWaterfallConfigResponse","description":"Result of creating (or reusing) a default pipeline."},"CreateDeploymentRequest":{"properties":{"source_ref":{"type":"string","maxLength":255,"minLength":1,"title":"Source Ref","description":"Immutable source reference (commit SHA). Branches move; deployments must not."},"schema_version_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Schema Version Id","description":"Schema version this build expects. Pinned so a rollback restores the matching schema, not merely the matching image."}},"type":"object","required":["source_ref"],"title":"CreateDeploymentRequest","description":"Start a deployment from a pinned source ref.\n\n``source_ref`` is a COMMIT-ish, not a branch name. A branch moves, so a\ndeployment recorded against one cannot answer \"what is running right now\" a\nweek later -- which is the question a rollback has to answer."},"CreateDynamicColumnRequest":{"properties":{"title":{"type":"string","title":"Title","description":"Display name of the column."},"data_type":{"type":"string","enum":["text","int","numeric","boolean"],"title":"Data Type","default":"text"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id","description":"Omit for a GLOBAL column, visible on every list in the org."}},"type":"object","required":["title"],"title":"CreateDynamicColumnRequest","description":"Add a custom column to a list, or globally."},"CreateEmptyListRequest":{"properties":{"title":{"type":"string","maxLength":200,"minLength":1,"title":"Title"},"source":{"type":"string","enum":["csv","graph8","FormSubmission","visitor","salesforce","hubspot","keyword","intent","workbench"],"title":"Source","description":"Where the list comes from, e.g. `csv`."},"type":{"type":"string","enum":["contacts","companies","suppressions","deals","leads"],"title":"Type","description":"What the list holds. The wire name is `type`; the app's field is `type_` because `type` is a Python builtin, and the alias keeps the wire name identical to the app's.","default":"contacts"},"status":{"type":"string","enum":["completed","processing","failed"],"title":"Status","default":"completed"},"is_dynamic":{"type":"boolean","title":"Is Dynamic","description":"A dynamic list re-runs its query; a static one keeps what it is given.","default":false},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"idempotency_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Idempotency Key","description":"Retry-safe: the same key returns the same list."},"request_fingerprint":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Request Fingerprint"}},"type":"object","required":["title","source"],"title":"CreateEmptyListRequest","description":"Create a list with nothing in it, to fill later.\n\n`idempotency_key` is worth using: without one, a retried create makes a\nSECOND empty list, and a duplicate list is harder to notice than a failed\nrequest."},"CreateEnrichmentConfigRequest":{"properties":{"name":{"type":"string","minLength":1,"title":"Name"},"type":{"type":"string","enum":["ai","waterfall"],"title":"Type"},"config":{"additionalProperties":true,"type":"object","title":"Config"},"column_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Column Id"},"field_to_enrich":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Field To Enrich"},"data_type":{"type":"string","title":"Data Type","default":"text"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"is_global":{"type":"boolean","title":"Is Global","default":true}},"type":"object","required":["name","type","config"],"title":"CreateEnrichmentConfigRequest","description":"Create an enrichment configuration.\n\nThe app takes this as a free dict and reads these keys. `type` is closed to\nthe two the handler validates; `ai` requires `group_id`, `prompt`, `model`,\n`usecase`, `input_mapping`, `outputs` and `column_mappings` inside\n`config`, and `waterfall` requires `column_id`, `field_to_enrich` and\n`config.steps`."},"CreateEnvelopeRequest":{"properties":{"subject":{"type":"string","minLength":1,"title":"Subject","description":"Subject line the signer sees."},"message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Message","description":"Covering note in the signing email."},"signer_name":{"type":"string","minLength":1,"title":"Signer Name"},"signer_email":{"type":"string","minLength":1,"title":"Signer Email"},"signer_contact_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Signer Contact Id","description":"Link the envelope to a graph8 contact record."},"source_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Type","description":"What produced this envelope, e.g. `quote`. Free-form, and filterable on list."},"source_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Id","description":"The producing record's id."},"expires_in_days":{"type":"integer","maximum":365.0,"minimum":1.0,"title":"Expires In Days","description":"How long the signing link stays valid, counted from CREATION rather than from send.","default":30},"documents":{"items":{"$ref":"#/components/schemas/EnvelopeDocument"},"type":"array","minItems":1,"title":"Documents","description":"At least one document - an empty envelope has nothing to sign."}},"type":"object","required":["subject","signer_name","signer_email","documents"],"title":"CreateEnvelopeRequest","description":"Create a DRAFT envelope. Nothing is emailed until it is sent.\n\nExactly one signer. The app's model carries one `signer_name` /\n`signer_email` pair rather than a list, so this does too - a mirror that\ninvented a list would accept a second signer that is silently dropped."},"CreateEventTypeRequest":{"properties":{"title":{"type":"string","title":"Title"},"slug":{"type":"string","title":"Slug"},"length":{"type":"integer","maximum":525600.0,"minimum":5.0,"title":"Length"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"locations":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Locations"},"booking_fields":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Booking Fields"},"scheduling_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Scheduling Type"},"schedule_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Schedule Id"},"time_zone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Time Zone"},"hidden":{"type":"boolean","title":"Hidden","default":false},"requires_confirmation":{"type":"boolean","title":"Requires Confirmation","default":false},"minimum_booking_notice":{"type":"integer","title":"Minimum Booking Notice","default":120},"before_event_buffer":{"type":"integer","title":"Before Event Buffer","default":0},"after_event_buffer":{"type":"integer","title":"After Event Buffer","default":0},"slot_interval":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Slot Interval"},"seats_per_time_slot":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Seats Per Time Slot"},"disable_guests":{"type":"boolean","title":"Disable Guests","default":false},"disable_cancelling":{"type":"boolean","title":"Disable Cancelling","default":false},"disable_rescheduling":{"type":"boolean","title":"Disable Rescheduling","default":false},"recurring_event":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Recurring Event"},"period_type":{"type":"string","title":"Period Type","default":"unlimited"},"period_start_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Period Start Date"},"period_end_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Period End Date"},"period_days":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Period Days"},"success_redirect_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Success Redirect Url"},"event_color":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Event Color"},"event_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Event Name"},"layouts":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Layouts"},"default_layout":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Default Layout"},"metadata":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Metadata"},"initial_hosts":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Initial Hosts"},"use_common_schedule":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Use Common Schedule"}},"type":"object","required":["title","slug","length"],"title":"CreateEventTypeRequest"},"CreateFieldEnrichmentInput":{"properties":{"type":{"type":"string","title":"Type","description":"Pipeline kind. Only 'waterfall' is supported today.","default":"waterfall"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Pipeline name. Defaults to `<column title> Enrichment` if omitted."},"field_to_enrich":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Field To Enrich","description":"Target field identifier. Defaults to the new column's slug."},"target_field":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Field","description":"Kind of data this column holds — CONTACT_DIRECT_PHONE, CONTACT_MOBILE_PHONE, CONTACT_WORK_EMAIL, CONTACT_LINKEDIN_URL, COMPANY_PHONE, ... or a friendly synonym ('phone', 'mobile', 'email', 'linkedin'). When set, the pipeline is built from the server's per-column TEMPLATE so each provider runs its CORRECT action for that data kind (e.g. leadmagic `mobile_finder` for a phone, NOT `email_finder`) — the same actions the web UI's 'Add column -> Waterfall' picks. Combine with `providers[]` to keep only those providers from the template. Mutually exclusive with `steps`. When omitted, the legacy `providers[]` email-finder shortcut is unchanged."},"skip_existing_values":{"type":"boolean","title":"Skip Existing Values","description":"If true, skip rows where the target field is already populated.","default":true},"providers":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Providers","description":"Ordered list of provider names. Without `target_field`, server maps each to its default email-finder action (legacy). With `target_field`, filters the column template to these providers (correct per-field action preserved). Mutually exclusive with `steps`."},"steps":{"anyOf":[{"items":{"$ref":"#/components/schemas/WaterfallStepInput"},"type":"array"},{"type":"null"}],"title":"Steps","description":"Full caller-supplied step list. Persisted verbatim. Mutually exclusive with `providers`."},"email_verification":{"anyOf":[{"$ref":"#/components/schemas/EmailVerificationInput"},{"type":"null"}],"description":"Optional post-enrichment email verification config."}},"type":"object","title":"CreateFieldEnrichmentInput","description":"Optional enrichment-pipeline block attached at column-create time.\n\nWhen supplied, `POST /fields` creates a companion `enrichment_configs`\nrow in the same request so the new column is immediately runnable via\n`POST /enrichment/waterfall/enrich`. Without this block the column\nexists but has no enrichment plan — calling /waterfall/enrich on it\nreturns 422 (`waterfall_config_missing`).\n\nCurrently only `type='waterfall'` is supported; AI / formula\nenrichment will follow once the rest of the agent surface lands."},"CreateFieldEnrichmentResponse":{"properties":{"column_id":{"type":"string","title":"Column Id","description":"column_id slug to pass to /enrichment/waterfall/enrich"},"config_id":{"type":"string","title":"Config Id"},"name":{"type":"string","title":"Name"},"type":{"type":"string","title":"Type"},"providers":{"items":{"type":"string"},"type":"array","title":"Providers"},"email_verification":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Email Verification"}},"type":"object","required":["column_id","config_id","name","type"],"title":"CreateFieldEnrichmentResponse","description":"Echo of the companion enrichment config created by `enrichment` block."},"CreateFieldRequest":{"properties":{"title":{"type":"string","title":"Title","description":"Column title, e.g. 'Job Level'"},"data_type":{"type":"string","title":"Data Type","description":"Column data type: 'text', 'int' (whole number), 'numeric' (decimal) or 'boolean' (yes/no). Unknown values 400. If the name already exists with another type, the create is rejected with 409.","default":"text"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id","description":"If set, field is list-specific; otherwise global across the org"},"entity":{"type":"string","title":"Entity","description":"Target entity: 'contacts' or 'companies'","default":"contacts"},"enrichment":{"anyOf":[{"$ref":"#/components/schemas/CreateFieldEnrichmentInput"},{"type":"null"}],"description":"Optional enrichment-pipeline block. When supplied, a companion `enrichment_configs` row is created in the same request so the new column is immediately runnable via /enrichment/waterfall/enrich."}},"type":"object","required":["title"],"title":"CreateFieldRequest","description":"Request body for creating a custom field (column)."},"CreateFieldResponse":{"properties":{"id":{"type":"integer","title":"Id"},"title":{"type":"string","title":"Title"},"data_type":{"type":"string","title":"Data Type"},"name":{"type":"string","title":"Name"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"is_global":{"type":"boolean","title":"Is Global"},"enrichment":{"anyOf":[{"$ref":"#/components/schemas/CreateFieldEnrichmentResponse"},{"type":"null"}],"description":"Populated when the request included an `enrichment` block. Use `enrichment.column_id` for subsequent /enrichment/waterfall/enrich calls."},"already_existed":{"type":"boolean","title":"Already Existed","description":"True when a column with this name already existed in this scope, so no new column was created and `id` is the existing column. A different `data_type` for an existing name is rejected with 409.","default":false},"existing_data_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Existing Data Type","description":"When `already_existed` is true: the existing column's data type."},"warnings":{"items":{"type":"string"},"type":"array","title":"Warnings","description":"Non-blocking notices, e.g. a column with the same name already exists org-wide, so the list now shows two columns with that name."}},"type":"object","required":["id","title","data_type","name","is_global"],"title":"CreateFieldResponse"},"CreateFieldsBatchRequest":{"properties":{"fields":{"items":{"$ref":"#/components/schemas/BatchFieldItem"},"type":"array","title":"Fields","description":"Columns to create (1-100)."},"entity":{"type":"string","title":"Entity","description":"Target entity for ALL columns: 'contacts' or 'companies'","default":"contacts"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id","description":"Shared list scope for all columns. REQUIRED if ANY field carries an `enrichment` block — waterfall pipelines are list-scoped."}},"type":"object","required":["fields"],"title":"CreateFieldsBatchRequest","description":"Create MANY custom columns in one request.\n\nAll columns are created in a single DB transaction with a SINGLE view\nrebuild — at 40-50 columns this replaces 40-50 view recreations with one."},"CreateFieldsBatchResponse":{"properties":{"entity":{"type":"string","title":"Entity"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"total_requested":{"type":"integer","title":"Total Requested"},"total_created":{"type":"integer","title":"Total Created","description":"Columns returned by this call, INCLUDING ones that already existed (unchanged meaning). `total_already_existed` says how many of them were existing columns."},"results":{"items":{"$ref":"#/components/schemas/BatchFieldResult"},"type":"array","title":"Results"},"total_already_existed":{"type":"integer","title":"Total Already Existed","description":"How many requested columns already existed and were returned as-is.","default":0}},"type":"object","required":["entity","total_requested","total_created","results"],"title":"CreateFieldsBatchResponse"},"CreateFormulaColumnsRequest":{"properties":{"formula":{"type":"string","minLength":1,"title":"Formula","description":"The G8X formula expression."},"output_columns":{"items":{"$ref":"#/components/schemas/FormulaOutputColumnDef"},"type":"array","maxItems":20,"minItems":1,"title":"Output Columns"},"description":{"anyOf":[{"type":"string","maxLength":4000},{"type":"null"}],"title":"Description"}},"type":"object","required":["formula","output_columns"],"title":"CreateFormulaColumnsRequest","description":"Create a formula column with one child column per output."},"CreateFormulaConfigRequest":{"properties":{"name":{"type":"string","title":"Name"},"field_to_enrich":{"type":"string","title":"Field To Enrich"},"data_type":{"type":"string","title":"Data Type","default":"text"},"config":{"$ref":"#/components/schemas/FormulaConfigDto"}},"type":"object","required":["name","field_to_enrich","config"],"title":"CreateFormulaConfigRequest","description":"Attach a formula to a column."},"CreateFormulaTemplateRequest":{"properties":{"name":{"type":"string","title":"Name"},"description":{"type":"string","title":"Description"},"prompt":{"type":"string","title":"Prompt"},"category":{"type":"string","title":"Category"},"target_type":{"type":"string","title":"Target Type","description":"'companies' or 'contacts'."},"output_type":{"type":"string","title":"Output Type","description":"'text', 'number' or 'boolean'."},"field_dependencies":{"items":{"type":"string"},"type":"array","title":"Field Dependencies"},"example_formula":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Example Formula"},"is_system_template":{"type":"boolean","title":"Is System Template","default":false}},"type":"object","required":["name","description","prompt","category","target_type","output_type","field_dependencies"],"title":"CreateFormulaTemplateRequest","description":"Save a reusable formula-authoring template."},"CreateFromDomainSampleContact":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"job_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Title"},"company_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Name"},"company_domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Domain"}},"type":"object","title":"CreateFromDomainSampleContact"},"CreateFromIdeaRequest":{"properties":{"format":{"type":"string","enum":["landing_page","linkedin_post","ad_creative","newsletter_section"],"title":"Format"}},"type":"object","required":["format"],"title":"CreateFromIdeaRequest","description":"Turn a mined idea into a draft. SPENDS CREDIT, immediately."},"CreateGridRequest":{"properties":{"name":{"type":"string","title":"Name"},"grid_type":{"type":"string","title":"Grid Type"},"workflow_config":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Workflow Config"}},"type":"object","required":["name","grid_type"],"title":"CreateGridRequest","description":"Create a content grid - a batch of content jobs. Spends nothing itself."},"CreateIcpRequest":{"properties":{"name":{"type":"string","title":"Name","description":"ICP name/title."},"website_url":{"type":"string","title":"Website Url","description":"The org website this ICP belongs to."},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Freeform ICP description."},"firmographics":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Firmographics","description":"Firmographic criteria (industry, size, geo, ...)."},"tech_stack":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Tech Stack","description":"Technology signals."},"buying_signals":{"anyOf":[{"items":{},"type":"array"},{"type":"null"}],"title":"Buying Signals","description":"List of buying-intent signals."},"estimated_market_size":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Estimated Market Size","description":"Estimated addressable-market count."}},"type":"object","required":["name","website_url"],"title":"CreateIcpRequest","description":"Body for POST /icps - create a Studio ICP manually (no AI generation).\n\nMirrors the internal Studio \"Add ICP\" action. Manual ICPs are created with\nstatus 'active'; the fit/opportunity/readiness/total scores stay null (they are\nonly produced by the AI generate flow, which this endpoint does not run)."},"CreateInterviewAttemptByCodeRequest":{"properties":{"call_id":{"type":"string","format":"uuid","title":"Call Id","description":"The practice call this attempt is made of."}},"type":"object","required":["call_id"],"title":"CreateInterviewAttemptByCodeRequest","description":"Record an attempt identified by the member's invite CODE rather than their id."},"CreateInterviewAttemptRequest":{"properties":{"call_id":{"type":"string","format":"uuid","title":"Call Id","description":"The practice call this attempt is made of."},"member_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Member Id","description":"Which member attempted it. Omit for an unattributed attempt."}},"type":"object","required":["call_id"],"title":"CreateInterviewAttemptRequest","description":"Record an attempt at an interview round, against a call that already exists."},"CreateInterviewRequest":{"properties":{"name":{"type":"string","minLength":1,"title":"Name","description":"What the round is called."},"audience_id":{"type":"string","minLength":1,"title":"Audience Id","description":"Audience the prospect is drawn from."},"prospect_id":{"type":"string","minLength":1,"title":"Prospect Id","description":"The contact the AI will play."},"prospect_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Prospect Name"},"behavior":{"type":"string","minLength":1,"title":"Behavior","description":"How the AI prospect behaves. Free-form: the app does not close this set.","default":"Nay-sayer"},"max_attempts":{"type":"integer","exclusiveMinimum":0.0,"title":"Max Attempts","description":"How many times a member may try.","default":3},"code_ttl_days":{"anyOf":[{"type":"integer","maximum":365.0,"exclusiveMinimum":0.0},{"type":"null"}],"title":"Code Ttl Days","description":"How long an invite code stays valid. Omit for the app default of 14 days."}},"type":"object","required":["name","audience_id","prospect_id"],"title":"CreateInterviewRequest","description":"Create an interview round - a scripted practice call a candidate is invited to."},"CreateLandingPageRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id"},"goal":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Goal"},"generate":{"type":"boolean","title":"Generate","description":"Run the AI generation pass. TRUE BY DEFAULT and it spends credit.","default":true},"generation_mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Generation Mode","default":"freeform"}},"type":"object","title":"CreateLandingPageRequest","description":"Create a landing page. SPENDS CREDIT when `generate` is true.\n\n`generate` true (the default) runs the full generation pass - copy, layout\nand imagery - against the org's brand context. Send `generate: false` for\nan empty shell you intend to fill with `/clone-url`, `/import-html` or the\ndeterministic edit routes, and nothing is spent."},"CreateListenerRequest":{"properties":{"platform":{"type":"string","enum":["x","linkedin","reddit","instagram","youtube"],"title":"Platform","default":"x"},"listener_type":{"type":"string","enum":["brand","competitor","keyword","engagement","user"],"title":"Listener Type","description":"`brand` and `competitor` watch a named entity, `keyword` watches a query, `engagement` watches an ICP-shaped bucket, `user` watches one account's posts."},"name":{"type":"string","minLength":1,"title":"Name"},"query":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Query","description":"Platform-native search query. OMITTING this on a `brand` listener makes the app build one with an LLM call, which SPENDS CREDITS. Supply a query, or call `POST /social-listeners/queries/generate` first if you want to see it before committing."},"target_handle":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Handle","description":"Required for a `user` listener: the account to watch."},"filters":{"additionalProperties":true,"type":"object","title":"Filters"},"poll_interval_sec":{"anyOf":[{"type":"integer","minimum":60.0},{"type":"null"}],"title":"Poll Interval Sec","description":"How often the worker polls. Shorter means more matches AND more spend."},"monthly_credit_cap":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Monthly Credit Cap","description":"Per-listener ceiling on credits. The one field that BOUNDS what this costs."},"force_rebuild_brand":{"type":"boolean","title":"Force Rebuild Brand","description":"Rebuild a brand query even though one exists. Spends a credit to do it.","default":false}},"type":"object","required":["listener_type","name"],"title":"CreateListenerRequest","description":"Start watching something. THIS CAN SPEND CREDITS.\n\nA `brand` listener with no `query` builds one with an LLM call, which is\ncharged. Every other combination writes a row and the polling worker does\nthe fetching from then on."},"CreateMasterListRequest":{"properties":{"title":{"type":"string","maxLength":500,"title":"Title"},"type":{"type":"string","enum":["contacts","companies","suppressions","deals","leads"],"title":"Type","description":"Wire name is `type`; see `CreateEmptyListRequest`.","default":"contacts"},"source_list_ids":{"items":{"type":"integer"},"type":"array","title":"Source List Ids","description":"The lists to union."},"include_all_sources":{"type":"boolean","title":"Include All Sources","description":"Take EVERY list of this type instead of the named ones, including ones created later. `source_list_ids` is then ignored.","default":false}},"type":"object","required":["title"],"title":"CreateMasterListRequest","description":"A list that is the UNION of other lists, kept in sync."},"CreateMeetingRequest":{"properties":{"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"start_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Start At","description":"ISO 8601."},"end_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"End At","description":"ISO 8601."},"location":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Location"},"contact_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Contact Ids","description":"CRM contact ids to associate."},"company_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Company Ids"},"deal_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Deal Ids"},"user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Id"}},"type":"object","title":"CreateMeetingRequest","description":"A meeting/event created on the CRM's calendar object."},"CreateOutOfOfficeRequest":{"properties":{"start":{"type":"string","title":"Start"},"end":{"type":"string","title":"End"},"notes":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Notes"},"public_note":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Public Note"},"to_user_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"To User Id"},"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason"},"time_zone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Time Zone"},"user_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"User Id"}},"type":"object","required":["start","end"],"title":"CreateOutOfOfficeRequest"},"CreatePageRequest":{"properties":{"url":{"type":"string","title":"Url"},"is_owned":{"type":"boolean","title":"Is Owned","default":true},"content_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Content Type","default":"website"},"content_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Content Status","default":"idea"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"}},"type":"object","required":["url"],"title":"CreatePageRequest","description":"Add one page to the content inventory. Spends nothing."},"CreatePausedSessionRequest":{"properties":{"user_id":{"type":"string","title":"User Id"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email"},"from_phone":{"type":"string","title":"From Phone"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"session_metadata":{"anyOf":[{"$ref":"#/components/schemas/SessionMetadataIn"},{"type":"null"}]},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id"},"campaign_builder_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Builder Campaign Id"},"parallel_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Parallel Count"},"dialing_mode":{"anyOf":[{"type":"string","enum":["power","parallel"]},{"type":"null"}],"title":"Dialing Mode"},"session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Id"}},"type":"object","required":["user_id","from_phone"],"title":"CreatePausedSessionRequest","description":"Mirrors `CreateSessionRequest` minus `org_id`. Dials NOBODY."},"CreatePersonaRequest":{"properties":{"title":{"type":"string","title":"Title","description":"Persona title (e.g. 'Director of Marketing Operations')."},"website_url":{"type":"string","title":"Website Url","description":"The org website this persona belongs to."},"priority":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Priority","description":"Display priority (lower sorts first). Defaults to 1."},"confidence":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Confidence","description":"Confidence label (e.g. 'high'/'medium'/'low'). Defaults to 'medium'."},"why_target":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Why Target","description":"Why this persona is worth targeting."},"key_signals":{"anyOf":[{"items":{},"type":"array"},{"type":"null"}],"title":"Key Signals","description":"List of buying/intent signals."},"expected_receptivity":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Expected Receptivity","description":"Expected receptivity note."},"campaign_approach":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Approach","description":"Recommended campaign approach."},"recommended_goal":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Recommended Goal","description":"Recommended campaign goal."},"source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source","description":"Origin label for the persona. Defaults to 'manual'."}},"type":"object","required":["title","website_url"],"title":"CreatePersonaRequest","description":"Body for POST /personas - create a Studio buyer persona manually.\n\nMirrors the internal Studio \"Add Persona\" action. Manual personas are created\nwith status 'active'; AI/score fields stay null (they are only populated by the\nAI generate flow, which this endpoint intentionally does not run)."},"CreateProgrammaticCampaignRequest":{"properties":{"name":{"type":"string","title":"Name"},"template_page_id":{"type":"string","title":"Template Page Id","description":"A landing page with HTML, from `GET /landing-pages`."},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"data_source_type":{"type":"string","enum":["list","workbench","csv","seo_import"],"title":"Data Source Type","default":"list"},"data_source_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Data Source Id"},"data_source_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Data Source Name"},"slug_template":{"type":"string","title":"Slug Template","default":"{{company}}-{{first_name}}"},"variable_config":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Variable Config"},"settings":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Settings"}},"type":"object","required":["name","template_page_id"],"title":"CreateProgrammaticCampaignRequest","description":"A template landing page plus a data source: one page per source row."},"CreateRoutingFormRequest":{"properties":{"name":{"type":"string","maxLength":255,"minLength":1,"title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"fields":{"items":{"$ref":"#/components/schemas/RoutingFormField"},"type":"array","title":"Fields"},"routes":{"items":{"$ref":"#/components/schemas/RoutingFormRouteInput"},"type":"array","title":"Routes"},"disabled":{"type":"boolean","title":"Disabled","default":false}},"type":"object","required":["name"],"title":"CreateRoutingFormRequest"},"CreateRoutingRuleRequest":{"properties":{"name":{"type":"string","title":"Name"},"source_list_id":{"type":"integer","title":"Source List Id"},"dest_list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Dest List Id"},"dest_list_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Dest List Name","description":"Create a new destination with this name."},"conditions":{"items":{"$ref":"#/components/schemas/ConditionDto"},"type":"array","title":"Conditions"},"formula_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Formula Text"},"ai_explanation":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Ai Explanation"},"column_config":{"$ref":"#/components/schemas/ColumnConfigDto"},"schedule_type":{"type":"string","enum":["one_time","continuous"],"title":"Schedule Type","description":"`continuous` keeps matching NEW records for as long as the rule exists.","default":"one_time"},"sync_mode":{"type":"string","enum":["all_matching","new_only"],"title":"Sync Mode","default":"all_matching"}},"type":"object","required":["name","source_list_id"],"title":"CreateRoutingRuleRequest","description":"Move records from one list to another when they match."},"CreateSavedFilterRequest":{"properties":{"title":{"type":"string","maxLength":120,"minLength":1,"title":"Title"},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description"},"state":{"additionalProperties":true,"type":"object","title":"State","description":"The filter itself. Opaque to this contract and round-tripped as-is."}},"additionalProperties":false,"type":"object","required":["title"],"title":"CreateSavedFilterRequest","description":"A named view over the bookings list.\n\nCLOSED (`extra=\"forbid\"`), mirroring the app, whose own DTO carries the\nsame with a reviewer note saying why: `state` is written into JSONB, so an\nunrecognised TOP-LEVEL key is a caller mistake, not a new feature."},"CreateScheduleRequest":{"properties":{"name":{"type":"string","title":"Name"},"time_zone":{"type":"string","title":"Time Zone"},"is_default":{"type":"boolean","title":"Is Default","default":false},"availability":{"anyOf":[{"items":{"$ref":"#/components/schemas/AvailabilityInput"},"type":"array"},{"type":"null"}],"title":"Availability"},"overrides":{"anyOf":[{"items":{"$ref":"#/components/schemas/OverrideInput"},"type":"array"},{"type":"null"}],"title":"Overrides"}},"type":"object","required":["name","time_zone"],"title":"CreateScheduleRequest"},"CreateSendingScheduleRequest":{"properties":{"name":{"type":"string","maxLength":255,"title":"Name"},"description":{"anyOf":[{"type":"string","maxLength":1024},{"type":"null"}],"title":"Description"},"timezone":{"type":"string","maxLength":128,"title":"Timezone","description":"IANA timezone.","default":"UTC"},"config":{"$ref":"#/components/schemas/SendingWeek"}},"type":"object","required":["name","config"],"title":"CreateSendingScheduleRequest","description":"A sending schedule. Mirrors `CreateSchedulePayload` minus the client `id`."},"CreateSequenceTemplateRequest":{"properties":{"name":{"type":"string","maxLength":255,"title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"textual_agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Textual Agent Name","description":"Agent for email / social steps."},"voice_agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Voice Agent Name","description":"Agent for phone / SMS steps."},"schedule_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Schedule Id","description":"Sending schedule, from `GET /schedules`."},"appointment_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Appointment Id","description":"Event type id for the booking link."},"steps":{"anyOf":[{"items":{"$ref":"#/components/schemas/SequenceTemplateStep"},"type":"array"},{"type":"null"}],"title":"Steps"}},"type":"object","required":["name"],"title":"CreateSequenceTemplateRequest","description":"A reusable sequence skeleton. Mirrors `CreateSequenceTemplatePayload`."},"CreateStepRequest":{"properties":{"name":{"type":"string","title":"Name"},"channel":{"type":"string","title":"Channel"},"mode":{"type":"string","title":"Mode"},"day":{"type":"integer","title":"Day"},"platform":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Platform"},"angle_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Angle Id"},"cta_type":{"type":"string","title":"Cta Type","default":"soft_ask"},"personalization_level":{"type":"string","title":"Personalization Level","default":"medium"},"constraints":{"additionalProperties":true,"type":"object","title":"Constraints"},"condition":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Condition"},"stop_on_reply":{"type":"boolean","title":"Stop On Reply","default":true}},"type":"object","required":["name","channel","mode","day"],"title":"CreateStepRequest"},"CreateStepTemplateRequest":{"properties":{"name":{"type":"string","title":"Name"},"input_type":{"type":"string","enum":["ON_DEMAND","AI_GENERATED_TEMPLATE","MANUAL_TEMPLATE"],"title":"Input Type"},"step_type":{"type":"string","enum":["PHONE","EMAIL","MANUAL_DIALER","HEYREACH","NETRION","SMS","WHATSAPP"],"title":"Step Type"},"step_data":{"additionalProperties":true,"type":"object","title":"Step Data","description":"The step's content: `subject` / `body` for email, `message_body` for SMS and WhatsApp, the `linkedin_*` fields for LinkedIn, `instructions` for AI generation. The same shape as `step_data` on `GET /sequences/{sequence_id}/steps`."}},"type":"object","required":["name","input_type","step_type","step_data"],"title":"CreateStepTemplateRequest","description":"A reusable piece of step content. Mirrors `CreateStepTemplatePayload`\nminus the client-supplied `id` (see the module docstring)."},"CreateSurveyRequest":{"properties":{"name":{"type":"string","maxLength":255,"minLength":1,"title":"Name"},"type":{"type":"string","pattern":"^(nps|csat)$","title":"Type"},"question_text":{"type":"string","minLength":1,"title":"Question Text"},"thank_you_copy":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Thank You Copy"},"template_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Template Id"},"delivery_channel":{"type":"string","pattern":"^(email|bridge|in_app)$","title":"Delivery Channel","default":"email"},"scale_min":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Scale Min"},"scale_max":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Scale Max"},"comment_mode":{"anyOf":[{"type":"string","pattern":"^(none|link|html)$"},{"type":"null"}],"title":"Comment Mode","default":"none"}},"type":"object","required":["name","type","question_text"],"title":"CreateSurveyRequest"},"CreateSurveyTriggerRequest":{"properties":{"trigger_kind":{"type":"string","pattern":"^(scheduled|list_entry|stage_entry)$","title":"Trigger Kind"},"sender_email":{"type":"string","format":"email","title":"Sender Email"},"subject":{"type":"string","maxLength":2000,"minLength":1,"title":"Subject"},"audience_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience Ref"},"stage_value":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage Value"},"cadence_days":{"anyOf":[{"type":"integer","maximum":3650.0,"minimum":1.0},{"type":"null"}],"title":"Cadence Days"},"sender_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sender Name"},"reply_to":{"anyOf":[{"type":"string","format":"email"},{"type":"null"}],"title":"Reply To"}},"type":"object","required":["trigger_kind","sender_email","subject"],"title":"CreateSurveyTriggerRequest","description":"Configure an automated-send binding (Phase 3, RFC §5).\n\n- ``scheduled``  : requires ``audience_ref`` + ``cadence_days`` (30/60/90).\n- ``list_entry`` : requires ``audience_ref`` (the watch list).\n- ``stage_entry``: requires ``stage_value`` (the to_stage slug)."},"CreateTestRequest":{"properties":{"mailbox_ids":{"items":{"type":"integer"},"type":"array","maxItems":20,"minItems":1,"title":"Mailbox Ids","description":"1-20 mailboxes. The app's own ceiling; each one costs credits."},"test_name":{"type":"string","title":"Test Name"},"frequency":{"type":"string","title":"Frequency","description":"`once`, `weekly`, `biweekly` or `monthly`. Anything but `once` keeps charging on that cadence until paused.","default":"once"},"receiver_types":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Receiver Types","description":"Which seed inboxes to test against, e.g. `personal_gmail`. Omit for the app's default panel - a narrower list tests less and costs the same."},"custom_subject":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Custom Subject"},"custom_body":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Custom Body"},"sending_interval":{"type":"integer","title":"Sending Interval","description":"Minutes between sends, spreading the test out.","default":1}},"type":"object","required":["mailbox_ids","test_name"],"title":"CreateTestRequest","description":"Run an inbox-placement test. THIS SPENDS CREDITS.\n\n20 credits per mailbox, charged when the test is created, not when it\nfinishes. `frequency` other than `once` creates a RECURRING schedule that\nkeeps charging - use `GET /placement/scheduled` to see what is running and\n`/pause` to stop it."},"CreateTriggerRequest":{"properties":{"name":{"type":"string","maxLength":255,"minLength":1,"title":"Name"},"event_type":{"type":"string","enum":["ingest","ai_complete","status_change"],"title":"Event Type"},"conditions":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Conditions"},"action_type":{"type":"string","enum":["run_ai","run_formula","export","webhook_notify"],"title":"Action Type"},"action_config":{"additionalProperties":true,"type":"object","title":"Action Config"},"enabled":{"type":"boolean","title":"Enabled","default":true}},"type":"object","required":["name","event_type","action_type"],"title":"CreateTriggerRequest","description":"React to rows as they arrive or change.\n\n`action_type: run_ai` enriches, and charges for, every matching row.\n`webhook_notify` posts to a URL you give in `action_config`."},"CreateVideoAssetFromLinkRequest":{"properties":{"url":{"type":"string","maxLength":2000,"minLength":1,"title":"Url"}},"type":"object","required":["url"],"title":"CreateVideoAssetFromLinkRequest","description":"Register a YouTube video by URL (Google Video campaigns)."},"CreateVideoCreativeRequest":{"properties":{"template_id":{"type":"string","maxLength":40,"minLength":1,"title":"Template Id"},"storyboard":{"$ref":"#/components/schemas/VideoStoryboard"},"name":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Name"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id"}},"type":"object","required":["template_id","storyboard"],"title":"CreateVideoCreativeRequest","description":"Assemble clips into a video ad on a template. Spends nothing itself -\nthe clips were paid for when they were generated."},"CreateVideoUploadUrlRequest":{"properties":{"content_type":{"type":"string","maxLength":100,"title":"Content Type","description":"video/mp4 | video/quicktime | video/webm"},"size_bytes":{"type":"integer","exclusiveMinimum":0.0,"title":"Size Bytes","description":"Exact file size — signed into the PUT; a different body length is refused"}},"type":"object","required":["content_type","size_bytes"],"title":"CreateVideoUploadUrlRequest","description":"Ask for a presigned R2 PUT for a browser-direct video upload."},"CreateWorkbenchBindingsRequest":{"properties":{"list_id":{"type":"integer","title":"List Id","description":"The list whose grid gains the columns."},"workflow_id":{"type":"string","title":"Workflow Id","description":"The workflow producing the values."},"bindings":{"items":{"$ref":"#/components/schemas/WorkbenchBindingItem"},"type":"array","minItems":1,"title":"Bindings","description":"At least one. The app refuses an empty set; so does this."}},"type":"object","required":["list_id","workflow_id","bindings"],"title":"CreateWorkbenchBindingsRequest","description":"Bind a workflow's outputs to columns on one list."},"CreateWorkbenchPipelineRequest":{"properties":{"name":{"type":"string","title":"Name"},"start":{"$ref":"#/components/schemas/PipelineStartConfig"},"steps":{"items":{"$ref":"#/components/schemas/WorkbenchPipelineStep"},"type":"array","title":"Steps"},"enabled":{"type":"boolean","title":"Enabled","default":false}},"type":"object","required":["name","start"],"title":"CreateWorkbenchPipelineRequest","description":"Create a workbench pipeline. `enabled: true` ARMS it on every new row."},"CreateWorkflowRequest":{"properties":{"name":{"type":"string","maxLength":255,"minLength":1,"title":"Name"},"trigger":{"type":"string","enum":["new_booking","before_event","after_event","booking_cancelled","booking_rescheduled"],"title":"Trigger"},"time":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Time"},"time_unit":{"anyOf":[{"type":"string","enum":["minutes","hours","days"]},{"type":"null"}],"title":"Time Unit"},"is_active_on_all":{"type":"boolean","title":"Is Active On All","default":false},"event_type_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Event Type Ids"},"steps":{"items":{"$ref":"#/components/schemas/WorkflowStepInput"},"type":"array","maxItems":20,"minItems":1,"title":"Steps"}},"type":"object","required":["name","trigger","steps"],"title":"CreateWorkflowRequest"},"CreatedAgentRunResponse":{"properties":{"work_item_id":{"type":"string","title":"Work Item Id"},"session_id":{"type":"string","title":"Session Id"},"workflow_started":{"type":"boolean","title":"Workflow Started","description":"False is NORMAL, not an error: the run is stored either way and no worker picked it up on this attempt. Poll the run rather than retrying the create, which would start a second one."},"workflow_started_reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Workflow Started Reason"}},"type":"object","required":["work_item_id","session_id","workflow_started"],"title":"CreatedAgentRunResponse"},"CreatedAppPageResponse":{"properties":{"page_id":{"type":"string","title":"Page Id"}},"type":"object","required":["page_id"],"title":"CreatedAppPageResponse"},"CreatedCredentialResponse":{"properties":{"app_id":{"type":"string","title":"App Id"},"client_org_id":{"type":"string","title":"Client Org Id"},"client_id":{"type":"string","title":"Client Id"},"revoked":{"type":"boolean","title":"Revoked","default":false},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"client_secret":{"type":"string","title":"Client Secret","description":"Shown ONCE. Store it now — only its hash is kept, so it cannot be retrieved again. Rotate by creating a new credential and revoking this one."}},"type":"object","required":["app_id","client_org_id","client_id","client_secret"],"title":"CreatedCredentialResponse","description":"The create response, and the ONLY time the secret is ever returned.\n\nOnly the SHA-256 is stored — `developer_app_credentials` has no column that\ncould hold a plaintext secret — so this response cannot be reissued. That is\nthe point: a secret the platform can re-read is a secret the platform can\nleak."},"CredentialResponse":{"properties":{"app_id":{"type":"string","title":"App Id"},"client_org_id":{"type":"string","title":"Client Org Id"},"client_id":{"type":"string","title":"Client Id"},"revoked":{"type":"boolean","title":"Revoked","default":false},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"}},"type":"object","required":["app_id","client_org_id","client_id"],"title":"CredentialResponse","description":"A service credential. Carries NO secret."},"CrmAddress":{"properties":{"street":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Street"},"street2":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Street2"},"city":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"City"},"state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"State"},"postal_code":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Postal Code"},"country":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country"},"address_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Address Type"}},"type":"object","title":"CrmAddress"},"CrmAudienceRequest":{"properties":{"list_name":{"type":"string","title":"List Name","description":"Audience title. Matched exactly; reused when it exists."},"connection_id":{"type":"string","title":"Connection Id","description":"The CRM connection this audience is for. Its provider is recorded on the audience as the source and as a `crm-import` tag, which is what lets a later sync tell CRM-imported rows from graph8-native ones."},"entity_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Type","description":"`contacts`, `companies`, `deals` or `leads`. Singular forms are accepted and pluralised by the app; anything unrecognised falls back to `contacts`. Omit for `contacts`."}},"type":"object","required":["list_name","connection_id"],"title":"CrmAudienceRequest","description":"Get, or create, the graph8 audience a CRM import lands in.\n\nIdempotent by TITLE: calling twice with the same `list_name` returns the\nsame audience with `created: false` rather than making a second one. That is\nwhat makes it safe to call before every import, and it is why this is not\n`POST /lists` - that one always creates."},"CrmAudienceResponse":{"properties":{"audience_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Audience Id"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source"},"created":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Created","description":"True only when THIS call created the audience; false when it already existed."}},"additionalProperties":true,"type":"object","title":"CrmAudienceResponse","description":"The audience, and whether this call is what created it."},"CrmCollection":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"CrmCollection","description":"A list of CRM records.\n\nA bare list from the app is surfaced as `items`; a named collection keeps\nits own key AND gains `items`, so a caller can page either shape without\nknowing which handler produced it."},"CrmCollectionPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"CrmCollectionPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape."},"CrmCompanyCreateRequest":{"properties":{"name":{"type":"string","title":"Name"},"domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain"},"website":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Website"},"industry":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Industry"},"employee_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Employee Count"},"annual_revenue":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Annual Revenue"},"address":{"anyOf":[{"$ref":"#/components/schemas/CrmAddress"},{"type":"null"}]},"phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone"},"custom_fields":{"items":{"$ref":"#/components/schemas/CrmCustomField"},"type":"array","title":"Custom Fields"}},"type":"object","required":["name"],"title":"CrmCompanyCreateRequest"},"CrmCompanyUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain"},"website":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Website"},"industry":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Industry"},"employee_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Employee Count"},"annual_revenue":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Annual Revenue"},"address":{"anyOf":[{"$ref":"#/components/schemas/CrmAddress"},{"type":"null"}]},"phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone"},"custom_fields":{"anyOf":[{"items":{"$ref":"#/components/schemas/CrmCustomField"},"type":"array"},{"type":"null"}],"title":"Custom Fields"}},"type":"object","title":"CrmCompanyUpdateRequest"},"CrmContactCreateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"emails":{"items":{"$ref":"#/components/schemas/CrmEmail"},"type":"array","title":"Emails"},"phones":{"items":{"$ref":"#/components/schemas/CrmPhone"},"type":"array","title":"Phones"},"company_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Id","description":"The CRM's company id, not graph8's."},"company_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Name"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"address":{"anyOf":[{"$ref":"#/components/schemas/CrmAddress"},{"type":"null"}]},"user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Id","description":"CRM owner. See `GET /integrations/crm/users`."},"custom_fields":{"items":{"$ref":"#/components/schemas/CrmCustomField"},"type":"array","title":"Custom Fields"},"tags":{"items":{"type":"string"},"type":"array","title":"Tags"},"source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source"}},"type":"object","title":"CrmContactCreateRequest","description":"A new contact, created in the CUSTOMER'S CRM."},"CrmContactUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"emails":{"anyOf":[{"items":{"$ref":"#/components/schemas/CrmEmail"},"type":"array"},{"type":"null"}],"title":"Emails"},"phones":{"anyOf":[{"items":{"$ref":"#/components/schemas/CrmPhone"},"type":"array"},{"type":"null"}],"title":"Phones"},"company_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Id"},"company_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Name"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"address":{"anyOf":[{"$ref":"#/components/schemas/CrmAddress"},{"type":"null"}]},"user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Id"},"is_active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Active"},"custom_fields":{"anyOf":[{"items":{"$ref":"#/components/schemas/CrmCustomField"},"type":"array"},{"type":"null"}],"title":"Custom Fields"},"tags":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Tags"}},"type":"object","title":"CrmContactUpdateRequest","description":"A partial update. Every field is optional; omitted fields are untouched.\n\n`emails`, `phones`, `custom_fields` and `tags` are optional LISTS rather\nthan list-with-default here, which is the difference that matters: on the\ncreate model an omitted list means \"none\", and on this one it means \"leave\nwhat is there\". Sending `[]` REPLACES with empty."},"CrmCustomField":{"properties":{"field_name":{"type":"string","title":"Field Name"},"field_value":{"title":"Field Value","description":"Required, but may be null - which is how a custom field is cleared."},"field_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Field Type"}},"type":"object","required":["field_name","field_value"],"title":"CrmCustomField","description":"One provider-side custom field.\n\n`field_name` is the CRM's API name, not its label. Read the valid names\nfrom `GET /integrations/crm/fields`; a name the provider does not have is\nrejected by the provider, not here."},"CrmDealCreateRequest":{"properties":{"name":{"type":"string","title":"Name"},"amount":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Amount"},"stage":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage","description":"Provider's pipeline stage. Omit to take the provider's default stage."},"probability":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Probability"},"close_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Close Date","description":"ISO 8601 date."},"type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Type"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"company_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Id"},"contact_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contact Id"},"user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Id"},"custom_fields":{"items":{"$ref":"#/components/schemas/CrmCustomField"},"type":"array","title":"Custom Fields"}},"type":"object","required":["name"],"title":"CrmDealCreateRequest"},"CrmDealUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"amount":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Amount"},"stage":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage"},"probability":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Probability"},"close_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Close Date"},"type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Type"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"company_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Id"},"contact_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contact Id"},"user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Id"},"custom_fields":{"anyOf":[{"items":{"$ref":"#/components/schemas/CrmCustomField"},"type":"array"},{"type":"null"}],"title":"Custom Fields"}},"type":"object","title":"CrmDealUpdateRequest"},"CrmEmail":{"properties":{"email":{"type":"string","title":"Email"},"email_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email Type","description":"Provider's own label, e.g. `work`. Passed through unchanged."}},"type":"object","required":["email"],"title":"CrmEmail"},"CrmFieldItem":{"properties":{"name":{"type":"string","title":"Name"},"slug":{"type":"string","title":"Slug"},"type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Type"},"required":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Required"},"label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Label"}},"type":"object","required":["name","slug"],"title":"CrmFieldItem"},"CrmFieldsResponse":{"properties":{"fields":{"items":{"$ref":"#/components/schemas/CrmFieldItem"},"type":"array","title":"Fields"}},"type":"object","title":"CrmFieldsResponse"},"CrmIntegrationResponse":{"properties":{"provider":{"type":"string","title":"Provider"},"status":{"type":"string","title":"Status"},"connection_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Connection Id"},"last_sync_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Sync At"},"connected_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Connected At"}},"type":"object","required":["provider","status"],"title":"CrmIntegrationResponse"},"CrmMigrationReportPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"CrmMigrationReportPayload","description":"A CRM migration's per-object report, or the signed links to its lossless archive."},"CrmObjectCatalogPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"CrmObjectCatalogPayload","description":"The CRM objects a connection can see, with an explicit `status` for unsupported or reconnect-needed states."},"CrmObjectFieldsPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"CrmObjectFieldsPayload","description":"Field names and types of one CRM object."},"CrmObjectSyncBindingCreateRequest":{"properties":{"connection_id":{"type":"string","maxLength":255,"minLength":1,"title":"Connection Id"},"direction":{"type":"string","enum":["pull","push"],"title":"Direction"},"crm_object_id":{"type":"string","maxLength":255,"minLength":1,"title":"Crm Object Id"},"object_definition_id":{"type":"string","format":"uuid","title":"Object Definition Id"},"match":{"$ref":"#/components/schemas/ObjectSyncMatch"},"fields":{"items":{"$ref":"#/components/schemas/ObjectSyncFieldRule"},"type":"array","maxItems":200,"minItems":1,"title":"Fields"},"relationships":{"items":{"$ref":"#/components/schemas/ObjectSyncRelationshipRule"},"type":"array","maxItems":20,"title":"Relationships"},"delete_policy":{"type":"string","enum":["ignore","archive"],"title":"Delete Policy","default":"ignore"},"enabled":{"type":"boolean","title":"Enabled","default":true},"acknowledged_deletions":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Acknowledged Deletions"}},"additionalProperties":false,"type":"object","required":["connection_id","direction","crm_object_id","object_definition_id","match","fields"],"title":"CrmObjectSyncBindingCreateRequest","description":"Create a one-direction sync of a CRM object into (pull) or from (push) a graph8 custom object."},"CrmObjectSyncBindingUpdateRequest":{"properties":{"connection_id":{"type":"string","maxLength":255,"minLength":1,"title":"Connection Id"},"enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Enabled"},"match":{"anyOf":[{"$ref":"#/components/schemas/ObjectSyncMatch"},{"type":"null"}]},"fields":{"anyOf":[{"items":{"$ref":"#/components/schemas/ObjectSyncFieldRule"},"type":"array","maxItems":200,"minItems":1},{"type":"null"}],"title":"Fields"},"relationships":{"anyOf":[{"items":{"$ref":"#/components/schemas/ObjectSyncRelationshipRule"},"type":"array","maxItems":20},{"type":"null"}],"title":"Relationships"},"delete_policy":{"anyOf":[{"type":"string","enum":["ignore","archive"]},{"type":"null"}],"title":"Delete Policy"},"acknowledged_deletions":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Acknowledged Deletions"},"resume":{"type":"boolean","title":"Resume","default":false}},"additionalProperties":false,"type":"object","required":["connection_id"],"title":"CrmObjectSyncBindingUpdateRequest","description":"Change a binding's mappings, match key, deletion policy or switch. `resume` clears a pause."},"CrmObjectSyncNewObjectRequest":{"properties":{"connection_id":{"type":"string","maxLength":255,"minLength":1,"title":"Connection Id"},"crm_object_id":{"type":"string","maxLength":255,"minLength":1,"title":"Crm Object Id"},"direction":{"type":"string","enum":["pull","push","both"],"title":"Direction"},"object":{"$ref":"#/components/schemas/ObjectSyncNewObjectSpec"},"match":{"$ref":"#/components/schemas/ObjectSyncNewMatch"},"fields":{"items":{"$ref":"#/components/schemas/ObjectSyncNewField"},"type":"array","maxItems":200,"minItems":1,"title":"Fields"},"delete_policy":{"type":"string","enum":["ignore","archive"],"title":"Delete Policy","default":"ignore"},"enabled":{"type":"boolean","title":"Enabled","default":true},"acknowledged_deletions":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Acknowledged Deletions"}},"additionalProperties":false,"type":"object","required":["connection_id","crm_object_id","direction","match","fields"],"title":"CrmObjectSyncNewObjectRequest","description":"Create the graph8 object from a CRM object, and its sync, in one transaction."},"CrmObjectSyncPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"CrmObjectSyncPayload","description":"An object-sync answer: capability, setup defaults, a binding, a run, a conflict list or a resolution."},"CrmObjectSyncPutRequest":{"properties":{"connection_id":{"type":"string","maxLength":255,"minLength":1,"title":"Connection Id"},"crm_object_id":{"type":"string","maxLength":255,"minLength":1,"title":"Crm Object Id"},"object_definition_id":{"type":"string","format":"uuid","title":"Object Definition Id"},"direction":{"type":"string","enum":["pull","push","both"],"title":"Direction"},"match":{"$ref":"#/components/schemas/ObjectSyncMatch"},"fields":{"items":{"$ref":"#/components/schemas/ObjectSyncFieldMapping"},"type":"array","maxItems":200,"minItems":1,"title":"Fields"},"relationships":{"items":{"$ref":"#/components/schemas/ObjectSyncRelationshipRule"},"type":"array","maxItems":20,"title":"Relationships"},"delete_policy":{"type":"string","enum":["ignore","archive"],"title":"Delete Policy","default":"ignore"},"enabled":{"type":"boolean","title":"Enabled","default":true},"acknowledged_deletions":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Acknowledged Deletions"}},"additionalProperties":false,"type":"object","required":["connection_id","crm_object_id","object_definition_id","direction","match","fields"],"title":"CrmObjectSyncPutRequest","description":"Set one CRM object's sync to pull, push or both. Both bindings are validated and written together."},"CrmObjectSyncResolveRequest":{"properties":{"connection_id":{"type":"string","maxLength":255,"minLength":1,"title":"Connection Id"},"crm_object_id":{"type":"string","maxLength":255,"minLength":1,"title":"Crm Object Id"},"crm_record_id":{"type":"string","maxLength":255,"minLength":1,"title":"Crm Record Id"},"action":{"type":"string","enum":["link","skip","archive","keep"],"title":"Action"},"record_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Record Id"}},"additionalProperties":false,"type":"object","required":["connection_id","crm_object_id","crm_record_id","action"],"title":"CrmObjectSyncResolveRequest","description":"Resolve one conflict row: link or skip an ambiguous match, archive or keep after a CRM deletion."},"CrmObjectSyncRunRequest":{"properties":{"connection_id":{"type":"string","maxLength":255,"minLength":1,"title":"Connection Id"},"direction":{"type":"string","enum":["pull","push"],"title":"Direction"}},"additionalProperties":false,"type":"object","required":["connection_id","direction"],"title":"CrmObjectSyncRunRequest","description":"Run a binding now, in its own direction."},"CrmPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"CrmPayload","description":"One CRM record, or one provider response.\n\nOpen-shaped ON PURPOSE. These bodies carry whatever the provider returned,\nthe field set differs between HubSpot, Salesforce, Pipedrive and SugarCRM,\nand it grows every time one of them ships something. Pinning it would drop\nwhatever a provider reported that this contract had not caught up on -\nwhich on a CRM surface means silently hiding the customer's own data from\nthem."},"CrmPhone":{"properties":{"phone":{"type":"string","title":"Phone"},"phone_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone Type"}},"type":"object","required":["phone"],"title":"CrmPhone"},"CrmProvider":{"type":"string","enum":["hubspot","salesforce","pipedrive","zoho","sugarcrm"],"title":"CrmProvider"},"CrmPushRequest":{"properties":{"records":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Records","description":"Records to push to the CRM provider"},"provider_fields":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Provider Fields","description":"Field mapping overrides"}},"type":"object","required":["records"],"title":"CrmPushRequest"},"CrmPushResponse":{"properties":{"pushed_count":{"type":"integer","title":"Pushed Count","default":0},"failed_count":{"type":"integer","title":"Failed Count","default":0},"errors":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Errors"}},"type":"object","title":"CrmPushResponse"},"CrmRecordPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"CrmRecordPayload","description":"An open envelope for one record, one dashboard or one job receipt.\n\nOpen because most of these reads are COMPUTED shapes - an engagement\nsummary, a next-best-step, an intelligence status - that grow with the\nproduct, and dropping a field from an advisory read makes it say \"nothing\nto report\" rather than \"we did not tell you\"."},"CrmReviewItemResolveRequest":{"properties":{"action":{"type":"string","enum":["create","link","skip"],"title":"Action"},"crm_record_id":{"anyOf":[{"type":"string","maxLength":255,"minLength":1},{"type":"null"}],"title":"Crm Record Id"}},"type":"object","required":["action"],"title":"CrmReviewItemResolveRequest","description":"Create the held-back contact in the CRM, link it to an existing CRM record, or skip it."},"CrmReviewQueuePayload":{"properties":{},"additionalProperties":true,"type":"object","title":"CrmReviewQueuePayload","description":"Contacts held back from CRM create because no CRM match was found, or the outcome of resolving one."},"CrmStatusResponse":{"properties":{"provider":{"type":"string","title":"Provider"},"connected":{"type":"boolean","title":"Connected"},"connection_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Connection Id"},"crm_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Crm Type"},"message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Message"},"last_sync_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Sync At"}},"type":"object","required":["provider","connected"],"title":"CrmStatusResponse"},"CrmSyncRunPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"CrmSyncRunPayload","description":"Sync-run history, a re-sync acceptance, the list-sync grid of a connection or its field access."},"CsvExportPayload":{"properties":{"content_type":{"type":"string","const":"text/csv","title":"Content Type","default":"text/csv"},"filename":{"type":"string","title":"Filename"},"csv":{"type":"string","title":"Csv","description":"The full CSV document, header row first."}},"type":"object","required":["filename","csv"],"title":"CsvExportPayload","description":"A CSV export, carried inside the JSON envelope.\n\nThe app streams these as `text/csv` attachments. Every other operation in\nthis contract answers with the `ApiResponse` envelope, and an SDK method\nthat sometimes returns JSON and sometimes a byte stream is a trap, so the\nCSV text is returned as a string field instead."},"CustomFieldDiConfigItem":{"properties":{"crm_provider":{"type":"string","title":"Crm Provider","description":"salesforce, hubspot or pipedrive."},"field_id":{"type":"string","maxLength":255,"title":"Field Id","description":"The CRM's own field id."},"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"display_name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Display Name"},"include_in_di_summary":{"type":"boolean","title":"Include In Di Summary","default":false},"include_in_forecast_probability":{"type":"boolean","title":"Include In Forecast Probability","default":false}},"type":"object","required":["crm_provider","field_id"],"title":"CustomFieldDiConfigItem","description":"One custom-field mapping.\n\nTyped rather than left an open dict: `crm_provider` and `field_id` are\nREQUIRED upstream, and an open list let a missing one reach the app's model\nas a raw ValidationError from inside the proxy - a 500 for a plain client\nerror. The 255 caps are the underlying VARCHAR widths, and `display_name`\nadditionally feeds the Deal Intelligence LLM prompt, so its bound is a\ntoken-budget and prompt-injection concern rather than cosmetic."},"CustomFieldDiConfigListResponse":{"properties":{"configs":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Configs"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"CustomFieldDiConfigListResponse","description":"Deal custom-field mappings for a CRM provider.\n\nThis is what a rebuilt deal form needs to know which custom fields exist\nand how they map outward - without it a custom UI can render the built-in\ncolumns and nothing else."},"CustomFieldDiConfigUpsertRequest":{"properties":{"items":{"items":{"$ref":"#/components/schemas/CustomFieldDiConfigItem"},"type":"array","maxItems":100,"minItems":1,"title":"Items"}},"type":"object","required":["items"],"title":"CustomFieldDiConfigUpsertRequest","description":"Replace the deal custom-field mappings.\n\n`items` is the FULL desired set for the providers it names, not a delta -\nthe app upserts what is sent. Capped at 100 by the app; declared here so an\nover-long request is a 422 naming the field rather than a failure deeper\nin."},"CustomFieldWriteReport":{"properties":{"written":{"items":{"type":"string"},"type":"array","title":"Written","description":"Caller keys that resolved to a custom column and were written."},"created":{"items":{"type":"string"},"type":"array","title":"Created","description":"Caller keys for which a NEW custom column was created by this request."},"ignored":{"items":{"type":"string"},"type":"array","title":"Ignored","description":"Caller keys that matched no custom column and were NOT written. Create the column first (POST /fields) or pass create_missing_fields=true."}},"type":"object","title":"CustomFieldWriteReport","description":"How a write path handled the request's custom (dynamic) column keys.\n\nShared by every Developer API write surface that accepts custom columns\n(``POST /contacts``, ``PUT /contacts/assert[/batch]``,\n``PUT /companies/assert[/batch]``).\n\nEvery field defaults to empty, so a client that ignores this object sees no\nbehavioural change. It exists because these keys were previously dropped\nwith NO caller-visible signal — the only trace was a server-side\n``logger.warning`` in ``append_to_audience``."},"CustomLayoutTemplateRequest":{"properties":{"idea":{"type":"string","title":"Idea","description":"Plain-language description of the page to build."},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Short title. Derived from the idea when omitted."},"attached_assets":{"items":{"$ref":"#/components/schemas/AttachedAsset"},"type":"array","title":"Attached Assets","description":"Images and videos the page must use. Max 5 images and 2 videos."},"plan":{"anyOf":[{"$ref":"#/components/schemas/LpPlan"},{"type":"null"}],"description":"An approved plan from the plan-preview step."}},"type":"object","required":["idea"],"title":"CustomLayoutTemplateRequest","description":"Mirrors `campaign_builder.routers.brand_kit.CustomLayoutTemplateRequest`.\n\n`plan` is the object `POST /brand-kit/layout-templates/custom/plan` returns.\nPassing it back is how you build the page you previewed rather than a new\ninterpretation of the same idea."},"CustomObjectCapabilitiesResponse":{"properties":{"version":{"type":"integer","title":"Version"},"capabilities":{"additionalProperties":{"type":"boolean"},"type":"object","title":"Capabilities"}},"type":"object","required":["version","capabilities"],"title":"CustomObjectCapabilitiesResponse"},"CustomTemplatePlanRequest":{"properties":{"idea":{"type":"string","title":"Idea","description":"Plain-language description of the page to plan."},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Short title."},"attached_assets":{"items":{"$ref":"#/components/schemas/AttachedAsset"},"type":"array","title":"Attached Assets","description":"Images and videos the plan must place."}},"type":"object","required":["idea"],"title":"CustomTemplatePlanRequest","description":"Mirrors `campaign_builder.routers.brand_kit.CustomPlanRequest`.\n\nThe preview half of the pair above. Builds nothing and stores nothing."},"CustomerMappingRequest":{"properties":{"mashup_company_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Mashup Company Id","description":"graph8 company id. Null removes the mapping."}},"type":"object","required":["mashup_company_id"],"title":"CustomerMappingRequest","description":"Link a Stripe customer to a graph8 company, or unlink it with null."},"CustomerSuccessDriveFolderConnectRequest":{"properties":{"folder_id":{"type":"string","title":"Folder Id","description":"Google Drive folder id."},"folder_name":{"type":"string","title":"Folder Name","description":"Folder name, as shown in Drive."},"local_folder_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Local Folder Key","description":"Which Library folder the files land in. Derived when omitted."},"local_folder_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Local Folder Name"},"library_folder_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Library Folder Id","description":"Library folder id. REPLACES any other mapping to the same Library folder."},"library_folder_path":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Library Folder Path"},"label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Label"}},"type":"object","required":["folder_id","folder_name"],"title":"CustomerSuccessDriveFolderConnectRequest","description":"Mirrors `csm.DriveFolderConnectRequest`."},"CustomerSuccessMeetingTranscriptLinkRequest":{"properties":{"transcript_id":{"type":"string","title":"Transcript Id","description":"The transcript to attach to this meeting."}},"type":"object","required":["transcript_id"],"title":"CustomerSuccessMeetingTranscriptLinkRequest","description":"Mirrors `csm.LinkTranscriptToMeetingRequest`."},"CustomerSuccessTranscriptLinkRequest":{"properties":{"account_id":{"type":"string","title":"Account Id","description":"The account the transcript belongs to."}},"type":"object","required":["account_id"],"title":"CustomerSuccessTranscriptLinkRequest","description":"Mirrors `csm.LinkTranscriptRequest`."},"DataFilePreviewResponse":{"properties":{"rows":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Rows"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"DataFilePreviewResponse","description":"A page of rows as they will be read, with the mapping applied.\n\nRows are open dicts: they are the customer's own columns, so there is no\nschema to pin."},"DataFileUploadResponse":{"properties":{"datafile_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Datafile Id"},"row_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Row Count","description":"Rows detected. The import pre-check budgets against this."},"columns":{"items":{"type":"string"},"type":"array","title":"Columns","description":"Detected column headers."}},"additionalProperties":true,"type":"object","title":"DataFileUploadResponse","description":"The stored file, and how many rows it turned out to have.\n\n`row_count` is the number a caller should budget against: the import\npre-check treats it as the UPPER BOUND on new contacts, so an import is\nrefused if that many would breach the org's contact limit - even though\nsome rows will resolve to updates rather than creates."},"DataPipelineItems":{"properties":{"items":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Items"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"DataPipelineItems","description":"A list of data-pipeline objects or log entries."},"DatafileImportRequest":{"properties":{"datafile_id":{"type":"string","minLength":1,"title":"Datafile Id","description":"Id of a previously uploaded datafile."},"column_mapping":{"anyOf":[{"additionalProperties":{"type":"string"},"type":"object"},{"type":"null"}],"title":"Column Mapping","description":"Source header -> column name."},"limit":{"anyOf":[{"type":"integer","maximum":100000.0,"minimum":1.0},{"type":"null"}],"title":"Limit"},"skip_duplicates":{"type":"boolean","title":"Skip Duplicates","default":true},"raw_source_column_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Raw Source Column Id"}},"type":"object","required":["datafile_id"],"title":"DatafileImportRequest","description":"Import rows from a datafile that has ALREADY been uploaded.\n\n`datafile_id` refers to an upload made elsewhere; this operation does not\naccept file content, which is why it fits the JSON envelope at all."},"DateRangeDto":{"properties":{"from":{"type":"string","format":"date","title":"From"},"to":{"type":"string","format":"date","title":"To"}},"type":"object","required":["from","to"],"title":"DateRangeDto"},"DealAssertRequest":{"properties":{"name":{"type":"string","title":"Name","description":"Deal name (match key)"},"company_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Id","description":"Company ID (match key, combined with name)"},"amount":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Amount"},"currency":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Currency"},"stage_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage Id"},"pipeline_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Pipeline Id"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"close_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Close Date"}},"type":"object","required":["name"],"title":"DealAssertRequest"},"DealAssertResponse":{"properties":{"action":{"type":"string","title":"Action","description":"'created' or 'updated'"},"deal_id":{"type":"string","title":"Deal Id"}},"type":"object","required":["action","deal_id"],"title":"DealAssertResponse"},"DealCollectionPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"DealCollectionPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape."},"DealCompanyRequest":{"properties":{"mashup_company_id":{"type":"integer","title":"Mashup Company Id","description":"The CANONICAL company id (`mashup_companies`), not a `cb_company_extensions` / ABM overlay id. The two are different tables with different ids and passing the wrong one attaches the deal to nothing."}},"type":"object","required":["mashup_company_id"],"title":"DealCompanyRequest","description":"Attach or change the company on a deal."},"DealContact":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id","description":"Link id, not the person id."},"person_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Person Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Role","description":"Role on THIS deal."},"buying_role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Buying Role","description":"General buying role from the contact record."},"is_primary":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Primary"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"}},"additionalProperties":true,"type":"object","title":"DealContact","description":"One person linked to a deal.\n\n`role` is the person's role on THIS deal (champion, decision_maker,\ninfluencer, blocker, coach, end_user). `buying_role` is their general\nbuying role on the contact record and is NOT deal-specific - the two are\nseparate fields in the app and conflating them loses the distinction\nbetween \"who this is\" and \"what they are to this deal\"."},"DealContactAssertRequest":{"properties":{"deal_id":{"type":"string","title":"Deal Id","description":"Deal ID to associate"}},"type":"object","required":["deal_id"],"title":"DealContactAssertRequest"},"DealContactCreateRequest":{"properties":{"person_id":{"type":"string","title":"Person Id","description":"Contact to link to the deal."},"role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Role","description":"Role on this deal: champion, decision_maker, influencer, blocker, coach or end_user. The app does not constrain the value, so it is left open here rather than declaring an enum this surface would then have to keep in lock-step."}},"type":"object","required":["person_id"],"title":"DealContactCreateRequest"},"DealContactListResponse":{"properties":{"contacts":{"items":{"$ref":"#/components/schemas/DealContact"},"type":"array","title":"Contacts"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"DealContactListResponse","description":"Everyone linked to a deal."},"DealContactRoleUpdateRequest":{"properties":{"role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Role","description":"Buying-committee role for this contact on this deal. One of: champion, decision_maker, influencer, blocker, coach, end_user. Pass null to clear the role."}},"type":"object","required":["role"],"title":"DealContactRoleUpdateRequest","description":"Body for `PUT /deals/{deal_id}/contacts/{contact_id}`.\n\n`role` is REQUIRED but nullable. That combination is the whole point of a\nPUT here: `{\"role\": \"champion\"}` sets it, `{\"role\": null}` clears it, and\nan empty body `{}` is a 422 rather than a silent no-op — a PUT that says\nnothing about the sub-resource it is replacing is a caller bug, and the\nalternative (treating omission as \"clear\") would delete data on a typo."},"DealCreateRequest":{"properties":{"name":{"type":"string","title":"Name","description":"Deal name"},"company_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Company Id","description":"Deprecated: the company is derived from the contacts. If sent, it must match; otherwise omit it."},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Deal description"},"amount":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Amount","description":"Deal monetary value"},"currency":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Currency","description":"Currency code (default: USD)","default":"USD"},"stage_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage Id","description":"Stage ID (from /deals/pipelines)"},"pipeline_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Pipeline Id","description":"Pipeline ID (defaults to org default)"},"close_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Close Date","description":"Expected close date (ISO 8601)"},"owner_id":{"type":"string","title":"Owner Id","description":"Deal owner (user id or email). Required."},"contact_ids":{"items":{"type":"integer"},"type":"array","minItems":1,"title":"Contact Ids","description":"mashup_contact_ids to associate with the deal (>=1 required; all must share one company)"},"allow_duplicate":{"type":"boolean","title":"Allow Duplicate","description":"Set true to create a deal even if one already exists for the company","default":false}},"type":"object","required":["name","owner_id","contact_ids"],"title":"DealCreateRequest"},"DealDetail":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"revision":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Revision","description":"Optimistic-concurrency token. None means this org has no revision tracking, so a save is unconditional - it does NOT mean 1."},"amount":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Amount"},"currency":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Currency"},"stage":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"pipeline_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Pipeline Id"},"stage_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage Id"},"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id"},"company_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Id"},"close_date":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Close Date"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated At"}},"additionalProperties":true,"type":"object","title":"DealDetail","description":"One deal, with the related data the detail page reads.\n\n`revision` is the optimistic-concurrency token. It is `None` when the org\nhas no canonical revision tracking provisioned - the app degrades rather\nthan 503ing a read - and a null there means an unconditional save, NOT\nrevision 1. Do not default it."},"DealDocumentUpdateRequest":{"properties":{"content":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Content","description":"The document body."},"structured_data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Structured Data","description":"The machine-readable half. Replaces, does not merge."}},"type":"object","title":"DealDocumentUpdateRequest","description":"Edit a generated deal document in place.\n\nMirrors `campaign_builder.models.deal_documents.UpdateDealDocumentRequest`.\nAn omitted field is left alone; `structured_data` REPLACES the stored\nobject rather than merging into it."},"DealFieldOverride":{"properties":{"field":{"type":"string","title":"Field"},"winner":{"type":"string","enum":["primary","secondary"],"title":"Winner"}},"type":"object","required":["field","winner"],"title":"DealFieldOverride","description":"Which side of the merge wins one field.\n\nWithout an override the app picks per its own rules. Name a field here to\ndecide it yourself - the only way to keep a value from the deal that is\nbeing merged AWAY."},"DealLineItemRecord":{"properties":{"id":{"type":"string","title":"Id"},"stripe_product_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stripe Product Id"},"stripe_price_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stripe Price Id"},"manual_product_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Manual Product Id"},"product_name":{"type":"string","title":"Product Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"quantity":{"type":"integer","title":"Quantity"},"unit_amount":{"type":"integer","title":"Unit Amount"},"discount_pct":{"type":"number","title":"Discount Pct"},"line_total":{"type":"integer","title":"Line Total"},"billing_frequency":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Billing Frequency"},"sort_order":{"type":"integer","title":"Sort Order"}},"type":"object","required":["id","product_name","quantity","unit_amount","discount_pct","line_total","sort_order"],"title":"DealLineItemRecord","description":"A deal line item. Money fields are in cents."},"DealLineItemWrite":{"properties":{"stripe_product_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stripe Product Id","description":"Catalog product id, when catalog-backed."},"stripe_price_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stripe Price Id","description":"Catalog price id, when catalog-backed."},"manual_product_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Manual Product Id","description":"Id of a manually-defined product."},"product_name":{"type":"string","maxLength":500,"minLength":1,"title":"Product Name"},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description"},"quantity":{"type":"integer","maximum":10000.0,"minimum":1.0,"title":"Quantity","default":1},"unit_amount":{"type":"integer","maximum":1000000000.0,"minimum":0.0,"title":"Unit Amount","description":"Unit price in cents."},"discount_pct":{"type":"number","maximum":100.0,"minimum":0.0,"title":"Discount Pct","default":0},"billing_frequency":{"anyOf":[{"type":"string","maxLength":50},{"type":"null"}],"title":"Billing Frequency"},"sort_order":{"type":"integer","title":"Sort Order","default":0}},"type":"object","required":["product_name","unit_amount"],"title":"DealLineItemWrite","description":"One line item in a replace request. Money is in CENTS.\n\n`line_total` is not accepted: the server recomputes it from\n`unit_amount`, `quantity` and `discount_pct`."},"DealLineItemsPayload":{"properties":{"deal_id":{"type":"string","title":"Deal Id"},"amount":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Amount"},"currency":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Currency"},"line_items":{"items":{"$ref":"#/components/schemas/DealLineItemRecord"},"type":"array","title":"Line Items"},"linked_quote_total":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Linked Quote Total"},"amount_mismatch":{"type":"boolean","title":"Amount Mismatch","default":false}},"type":"object","required":["deal_id"],"title":"DealLineItemsPayload","description":"A deal's line items with its derived amount and quote-mismatch flag.\n\n`amount` and `linked_quote_total` are in DOLLARS (the deal's own unit);\nline-item money is in cents. `amount_mismatch` is true when the deal amount\nand its most authoritative linked quote disagree by more than half a cent."},"DealLineItemsReplaceBody":{"properties":{"line_items":{"items":{"$ref":"#/components/schemas/DealLineItemWrite"},"type":"array","title":"Line Items"}},"type":"object","title":"DealLineItemsReplaceBody","description":"The FULL desired set of line items. An empty list clears them."},"DealListResponse":{"properties":{"deals":{"items":{"$ref":"#/components/schemas/DealSummary"},"type":"array","title":"Deals"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"DealListResponse","description":"A page of deals on one account."},"DealMovePipelineRequest":{"properties":{"target_pipeline_id":{"type":"string","title":"Target Pipeline Id","description":"Pipeline to move the deal into."}},"type":"object","required":["target_pipeline_id"],"title":"DealMovePipelineRequest","description":"Move a deal to a different pipeline.\n\nThe deal keeps its identity and history; only its pipeline and stage\nchange. Its current stage does NOT carry over - the target pipeline has\nits own stages, and the app re-seats the deal within them."},"DealNoteMention":{"properties":{"id":{"type":"string","title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"}},"type":"object","required":["id"],"title":"DealNoteMention"},"DealNoteUpdateRequest":{"properties":{"content":{"type":"string","title":"Content","description":"Full replacement body - this is not a patch."},"mentioned_users":{"items":{"$ref":"#/components/schemas/DealNoteMention"},"type":"array","title":"Mentioned Users","description":"Who is mentioned AFTER the edit. Omitting someone removes their mention, because the list replaces rather than adds."}},"type":"object","required":["content"],"title":"DealNoteUpdateRequest","description":"Rewrite a note's body and its mentions."},"DealOpResponse":{"properties":{},"additionalProperties":true,"type":"object","title":"DealOpResponse","description":"Whatever the operation returns, carried through whole."},"DealPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"DealPayload","description":"An open envelope for a deal, a merge preview or a column result.\n\nOpen because the crossfire and merge-preview payloads are computed shapes\nthat grow with the product, and a closed model would drop a field from an\nADVISORY read - where a missing signal reads as \"nothing to worry about\"\nrather than \"we did not tell you\"."},"DealResponse":{"properties":{"revision":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Revision","description":"CRM revision after a conditional update"},"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"amount":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Amount"},"currency":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Currency"},"stage_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage Id"},"stage_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage Name"},"pipeline_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Pipeline Id"},"pipeline_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Pipeline Name"},"company_id":{"anyOf":[{},{"type":"null"}],"title":"Company Id"},"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id"},"owner_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Name"},"owner_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Email"},"last_activity_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Activity At"},"close_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Close Date"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"},"closed_lost_reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Closed Lost Reason"},"contact_count":{"type":"integer","title":"Contact Count","default":0},"primary_contact":{"anyOf":[{"$ref":"#/components/schemas/ContactBrief"},{"type":"null"}]},"contacts":{"anyOf":[{"items":{"$ref":"#/components/schemas/ContactBrief"},"type":"array"},{"type":"null"}],"title":"Contacts"}},"type":"object","title":"DealResponse"},"DealStageVelocityBucket":{"properties":{"stage_id":{"type":"string","title":"Stage Id"},"stage_name":{"type":"string","title":"Stage Name"},"position":{"type":"integer","title":"Position"},"avg_days_in_stage":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Avg Days In Stage"},"completed_dwells":{"type":"integer","title":"Completed Dwells"},"entered_count":{"type":"integer","title":"Entered Count"},"progressed_count":{"type":"integer","title":"Progressed Count"},"fell_back_count":{"type":"integer","title":"Fell Back Count"},"still_in_stage_count":{"type":"integer","title":"Still In Stage Count"},"conversion_rate":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Conversion Rate"}},"type":"object","required":["stage_id","stage_name","position","completed_dwells","entered_count","progressed_count","fell_back_count","still_in_stage_count"],"title":"DealStageVelocityBucket","description":"Movement through one stage.\n\n`avg_days_in_stage` and `conversion_rate` are null (not 0) when there is no\nsample: an average over zero completed dwells is undefined."},"DealStageVelocityPayload":{"properties":{"by_stage":{"items":{"$ref":"#/components/schemas/DealStageVelocityBucket"},"type":"array","title":"By Stage"},"stuck_deals":{"$ref":"#/components/schemas/DealStageVelocityStuckSummary"},"disclosures":{"items":{"type":"string"},"type":"array","title":"Disclosures"}},"type":"object","required":["stuck_deals"],"title":"DealStageVelocityPayload"},"DealStageVelocityStuckDeal":{"properties":{"deal_id":{"type":"string","title":"Deal Id"},"deal_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Deal Name"},"stage_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage Id"},"stage_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage Name"},"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id"},"owner_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Name"},"days_in_current_stage":{"type":"integer","title":"Days In Current Stage"},"last_transitioned_at":{"type":"string","format":"date-time","title":"Last Transitioned At"}},"type":"object","required":["deal_id","days_in_current_stage","last_transitioned_at"],"title":"DealStageVelocityStuckDeal"},"DealStageVelocityStuckSummary":{"properties":{"threshold_days":{"type":"integer","title":"Threshold Days"},"total_count":{"type":"integer","title":"Total Count"},"truncated":{"type":"boolean","title":"Truncated"},"deals":{"items":{"$ref":"#/components/schemas/DealStageVelocityStuckDeal"},"type":"array","title":"Deals"}},"type":"object","required":["threshold_days","total_count","truncated"],"title":"DealStageVelocityStuckSummary","description":"`total_count` is exact; `deals` is capped at 100 (`truncated` says so)."},"DealSummary":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"amount":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Amount"},"currency":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Currency"},"stage":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"pipeline_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Pipeline Id"},"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id"},"close_date":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Close Date"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"}},"additionalProperties":true,"type":"object","title":"DealSummary","description":"One deal as it appears in a list."},"DealTouchSearchPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"DealTouchSearchPayload","description":"Candidate touches found in the deal owner's Sent mail (`candidates`), each with a short-lived `token`."},"DealTouchSettingsPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"DealTouchSettingsPayload","description":"The organisation's deal-touch capture settings, or the caller's own status (`/me`)."},"DealTouchSettingsRequest":{"properties":{"enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Enabled"},"lookback_days":{"anyOf":[{"type":"integer","maximum":365.0,"minimum":14.0},{"type":"null"}],"title":"Lookback Days","description":"How far back to match touches to a deal."},"sent_capture":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Sent Capture","description":"Capture reps' sent mail as touches. Cannot be on while `enabled` is false."}},"type":"object","title":"DealTouchSettingsRequest","description":"A partial update: only the fields sent change."},"DealTouchTimelinePayload":{"properties":{},"additionalProperties":true,"type":"object","title":"DealTouchTimelinePayload","description":"A deal's touch timeline (`items`, `first_touch`, `last_touch`, `touch_count`) or one added touch."},"DealUpdateRequest":{"properties":{"expected_revision":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Expected Revision","description":"Apply only if the canonical CRM revision still matches; otherwise return 409. Omit for existing PATCH behavior."},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Deal name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Deal description"},"amount":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Amount","description":"Deal monetary value"},"currency":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Currency","description":"Currency code"},"stage_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage Id","description":"Stage ID"},"close_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Close Date","description":"Expected close date (ISO 8601)"},"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id","description":"Reassign deal owner (member id, email, or PropelAuth uid). Cannot be cleared."},"add_contact_ids":{"items":{"type":"integer"},"type":"array","title":"Add Contact Ids","description":"mashup_contact_ids to add to the deal (must match the deal's company; idempotent)"},"remove_contact_ids":{"items":{"type":"integer"},"type":"array","title":"Remove Contact Ids","description":"mashup_contact_ids to remove from the deal (idempotent — unlinked skipped)"},"contact_roles":{"anyOf":[{"additionalProperties":{"anyOf":[{"type":"string"},{"type":"null"}]},"type":"object"},{"type":"null"}],"title":"Contact Roles","description":"Buying-committee roles keyed by mashup_contact_id, e.g. {\"5500429\": \"champion\", \"5500914\": null}. Valid roles: champion, decision_maker, influencer, blocker, coach, end_user. null clears a role. Each id must already be linked to the deal or be present in add_contact_ids in the same request (422 otherwise)."}},"type":"object","title":"DealUpdateRequest"},"DecideAgentApprovalRequest":{"oneOf":[{"properties":{"decision":{"enum":["approve","reject","edit_and_approve"]},"use_human_authorization":{"const":false}},"required":["decision"]},{"properties":{"use_human_authorization":{"const":true}},"additionalProperties":false,"required":["use_human_authorization"]}],"properties":{"decision":{"anyOf":[{"type":"string","enum":["approve","reject","edit_and_approve"]},{"type":"null"}],"title":"Decision"},"use_human_authorization":{"type":"boolean","title":"Use Human Authorization","default":false},"edit_payload":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Edit Payload","description":"The redirected step, for 'edit_and_approve'. Ignored for the other decisions."}},"type":"object","title":"DecideAgentApprovalRequest","description":"Decide directly, or relay a stored human authorization exclusively.\n\nThere is no client-supplied version to pass. Double-decide is settled\nserver-side by `WHERE decided_at IS NULL`, so exactly one caller wins and the\nloser gets 409 rather than overwriting the first decision."},"DefaultConferencingEnvelope":{"properties":{"data":{"$ref":"#/components/schemas/DefaultConferencingResponse"}},"type":"object","required":["data"],"title":"DefaultConferencingEnvelope","description":"Envelope for GET/POST conferencing default. Inner fields are all-Optional\n(``null`` when nothing is configured), so the envelope is what carries the\nreal payload through response validation."},"DefaultConferencingResponse":{"properties":{"provider":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Provider"},"credential_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Credential Id"},"link":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Link"}},"type":"object","title":"DefaultConferencingResponse"},"DeleteCompaniesFromListRequest":{"properties":{"company_ids":{"items":{"type":"integer"},"type":"array","title":"Company Ids"}},"type":"object","title":"DeleteCompaniesFromListRequest"},"DeleteFieldResponse":{"properties":{"column_id":{"type":"integer","title":"Column Id"},"deleted":{"type":"boolean","title":"Deleted","default":true}},"type":"object","required":["column_id"],"title":"DeleteFieldResponse"},"DeleteLeadsFromListRequest":{"properties":{"lead_ids":{"items":{"type":"integer"},"type":"array","title":"Lead Ids","description":"The leads to remove."}},"type":"object","required":["lead_ids"],"title":"DeleteLeadsFromListRequest"},"DeleteSuppressionsFromListRequest":{"properties":{"suppression_ids":{"items":{"type":"integer"},"type":"array","title":"Suppression Ids","description":"The suppressions to remove."}},"type":"object","required":["suppression_ids"],"title":"DeleteSuppressionsFromListRequest"},"DeliverabilityListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"DeliverabilityListPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape."},"DeliverabilityPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"DeliverabilityPayload","description":"An open envelope for a test, a schedule or a warmup report.\n\nOpen because placement results carry one panel per seed provider and the\nprovider set changes; a closed model would drop a panel, and a missing\npanel on a deliverability report reads as \"we did not test there\" when the\ntruth may be \"you did not land there\"."},"DeltaSyncRequest":{"properties":{"connection_id":{"type":"string","title":"Connection Id"},"since":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Since","description":"ISO 8601 timestamp. Omit and the app picks the last successful watermark - which is usually what you want, and always safer than guessing one."},"entity_types":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Entity Types","description":"Limit to these entity types. Omit for all."},"recover_missing":{"type":"boolean","title":"Recover Missing","description":"Also re-fetch records the previous run should have imported and did not. Slower, and the reason to use it is a suspected gap rather than routine.","default":false}},"type":"object","required":["connection_id"],"title":"DeltaSyncRequest","description":"Import only what changed since a watermark.\n\nThe response echoes `since` back as ISO 8601, so the caller learns the\nwatermark the server actually used rather than assuming its own was\naccepted."},"DepartmentEntry":{"properties":{"id":{"type":"string","title":"Id","default":""},"name":{"type":"string","maxLength":64,"minLength":1,"title":"Name"},"slug":{"type":"string","maxLength":64,"minLength":1,"title":"Slug"},"description":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Description"},"color":{"anyOf":[{"type":"string","maxLength":9},{"type":"null"}],"title":"Color"},"sort_order":{"type":"integer","title":"Sort Order","default":0},"hidden":{"type":"boolean","title":"Hidden","default":false},"is_system_seed":{"type":"boolean","title":"Is System Seed","default":false}},"type":"object","required":["name","slug"],"title":"DepartmentEntry"},"DependentOut":{"properties":{"attribute_slug":{"type":"string","title":"Attribute Slug"},"title":{"type":"string","title":"Title"},"object_slug":{"type":"string","title":"Object Slug"},"through":{"items":{"type":"string"},"type":"array","title":"Through","description":"The computed fields between the field and this one, nearest the field first; empty for a direct reader."}},"type":"object","required":["attribute_slug","title","object_slug"],"title":"DependentOut"},"DependentsResponse":{"properties":{"dependents":{"items":{"$ref":"#/components/schemas/DependentOut"},"type":"array","title":"Dependents"},"hidden_dependents":{"type":"integer","title":"Hidden Dependents","description":"Dependents the caller may not see: counted here, never named.","default":0}},"type":"object","title":"DependentsResponse","description":"Every computed field that is computed from a field, directly or through others (other objects included)."},"DeploymentProgressRequest":{"properties":{"status":{"type":"string","enum":["building","promoting","failed"],"title":"Status","description":"Where the build has reached. `deployed` is not settable here -- taking traffic is a separate, builder-initiated promote."},"image_digest":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Image Digest","description":"The pushed image digest, once there is one. Reported with `promoting`."},"last_error_sanitized":{"anyOf":[{"type":"string","maxLength":4000},{"type":"null"}],"title":"Last Error Sanitized","description":"A short, ALREADY-SANITIZED failure reason, surfaced to the builder. Build logs carry secrets and other tenants' identifiers, so the controller sanitizes before sending and this field is truncated here."}},"type":"object","required":["status"],"title":"DeploymentProgressRequest","description":"What the in-cluster build controller reports as a build advances (J2).\n\nTHE ALLOWED SET IS `building | promoting | failed`, AND `deployed` IS ABSENT\nON PURPOSE. The controller knows when a build started and when an image is\npushed and ready. It does not decide that the app should take traffic; that is\n`POST .../promote`, a separate act by the builder. Letting the callback write\n`deployed` would collapse \"the build finished\" and \"send users at it\" into one\nstep performed by whichever pod happened to run the build.\n\n`rolled_back` is likewise absent: a rollback is a decision about a deployment\nthat is already serving, which a builder makes."},"DeploymentResponse":{"properties":{"deployment_id":{"type":"string","title":"Deployment Id"},"app_id":{"type":"string","title":"App Id"},"status":{"type":"string","title":"Status"},"source_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Ref"},"image_digest":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Image Digest"},"schema_version_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Schema Version Id"},"last_error_sanitized":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Error Sanitized","description":"Sanitized at the write. Build logs carry secrets and other tenants' ids."},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"deployed_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Deployed At"},"build_started_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Build Started At","description":"When the build started. `null` means it was not measured."},"build_finished_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Build Finished At","description":"When the build ended, at `promoting` or at `failed`. Not at `deployed`: that is reached after traffic is taken, so measuring to it would count promotion and rollout as build time."},"build_seconds":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Build Seconds","description":"Measured build duration. `null` means NOT MEASURED, never zero: a build whose transitions were not reported has no duration, and a metering pipeline reading 0 would bill nothing and look correct."}},"type":"object","required":["deployment_id","app_id","status"],"title":"DeploymentResponse"},"DeprecateKnowledgeRequest":{"properties":{"reason":{"type":"string","maxLength":2000,"minLength":1,"title":"Reason"},"superseded_by":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Superseded By"}},"type":"object","required":["reason"],"title":"DeprecateKnowledgeRequest","description":"Retire a concept. `reason` is required and is kept on the record."},"DesignTokenBadge":{"properties":{"background":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Background"},"text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Text"}},"type":"object","title":"DesignTokenBadge","description":"Unread launcher-badge colors (hex-validated)."},"DesignTokenColors":{"properties":{"surface":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Surface","description":"Widget body bg (light)"},"textPrimary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Textprimary"},"textSecondary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Textsecondary"},"border":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Border"},"link":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Link"},"bubbleAssistantBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bubbleassistantbg"},"bubbleAssistantText":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bubbleassistanttext"},"bubbleUserBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bubbleuserbg"},"bubbleUserText":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bubbleusertext"},"launcherBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Launcherbg"},"launcherIcon":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Launchericon"},"headerGradientFrom":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Headergradientfrom"},"headerGradientTo":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Headergradientto"},"heroText":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Herotext","description":"Home hero greeting text"},"heroTextMuted":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Herotextmuted","description":"Home hero subtitle text"},"askCardBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Askcardbg","description":"Ask-a-question card bg (light)"},"askCardBorder":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Askcardborder","description":"Ask-a-question card border (light)"},"askCardText":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Askcardtext","description":"Ask-a-question card text (light)"},"actionCardBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Actioncardbg","description":"Quick-action card bg (light)"},"actionCardBorder":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Actioncardborder","description":"Quick-action card border (light)"},"actionCardText":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Actioncardtext","description":"Quick-action card label (light)"},"actionCardIconTint":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Actioncardicontint","description":"Quick-action icon-circle tint (light)"},"agentBubbleBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agentbubblebg","description":"Human-agent bubble bg (light)"},"agentBubbleBorder":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agentbubbleborder","description":"Human-agent bubble border (light)"},"agentBubbleText":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agentbubbletext","description":"Human-agent bubble text (light)"},"sendButtonBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sendbuttonbg","description":"Composer send-button bg"},"sendButtonIcon":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sendbuttonicon","description":"Composer send-button icon"},"messagesTitleText":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Messagestitletext","description":"Messages screen title text"},"messagesSearchBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Messagessearchbg","description":"Messages search bar bg (light)"},"messagesSearchText":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Messagessearchtext","description":"Messages search text (light)"},"messagesSearchBorder":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Messagessearchborder","description":"Messages search bar border (opt-in)"},"typingDot":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Typingdot","description":"Typing-indicator dot (light)"},"slotChipBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slotchipbg","description":"Slot-picker chip bg (light)"},"slotChipText":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slotchiptext","description":"Slot-picker chip text (light)"},"slotChipHoverBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slotchiphoverbg","description":"Slot-picker chip hover bg (light)"},"slotChipHoverBorder":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slotchiphoverborder","description":"Slot-picker chip hover border (light)"}},"type":"object","title":"DesignTokenColors","description":"Color slots consumed by the widget's --wcw-* CSS var vocabulary.\n\nLIGHT-mode and mode-invariant leaves ONLY. Per-mode dark variants live on the\nsibling ``DesignTokenColorsDark`` group (``designTokens.colorsDark``), NOT as\n``*Dark`` twins here (Phase G). The ``@field_validator(\"*\")`` hex guard below\nis exactly WHY the dark palette must be a sibling group rather than a nested\n``colors.dark`` object — a nested dict would be fed to ``_require_hex_color``\nand 422 the save (the same force that made ``DesignTokenHeader`` separate).\nA legacy stored ``colors.<name>Dark`` leaf is lifted into ``colorsDark`` at\nparse time by ``DesignTokens._lift_legacy_dark_leaves`` — no data migration."},"DesignTokenColorsDark":{"properties":{"surface":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Surface","description":"Widget body bg (dark)"},"askCardBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Askcardbg","description":"Ask-a-question card bg (dark)"},"askCardBorder":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Askcardborder","description":"Ask-a-question card border (dark)"},"askCardText":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Askcardtext","description":"Ask-a-question card text (dark)"},"actionCardBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Actioncardbg","description":"Quick-action card bg (dark)"},"actionCardBorder":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Actioncardborder","description":"Quick-action card border (dark)"},"actionCardText":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Actioncardtext","description":"Quick-action card label (dark)"},"actionCardIconTint":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Actioncardicontint","description":"Quick-action icon-circle tint (dark)"},"agentBubbleBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agentbubblebg","description":"Human-agent bubble bg (dark)"},"agentBubbleBorder":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agentbubbleborder","description":"Human-agent bubble border (dark)"},"agentBubbleText":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agentbubbletext","description":"Human-agent bubble text (dark)"},"messagesSearchBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Messagessearchbg","description":"Messages search bar bg (dark)"},"messagesSearchText":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Messagessearchtext","description":"Messages search text (dark)"},"textPrimary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Textprimary","description":"Message text (dark)"},"textSecondary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Textsecondary","description":"Timestamps & meta text (dark)"},"border":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Border","description":"Borders & dividers (dark)"},"bubbleAssistantBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bubbleassistantbg","description":"Bot bubble bg (dark)"},"bubbleAssistantText":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bubbleassistanttext","description":"Bot bubble text (dark)"},"typingDot":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Typingdot","description":"Typing-indicator dot (dark)"},"slotChipBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slotchipbg","description":"Slot-picker chip bg (dark)"},"slotChipText":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slotchiptext","description":"Slot-picker chip text (dark)"},"slotChipHoverBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slotchiphoverbg","description":"Slot-picker chip hover bg (dark)"},"slotChipHoverBorder":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slotchiphoverborder","description":"Slot-picker chip hover border (dark)"},"composerPopoverBg":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Composerpopoverbg","description":"Composer emoji-popover bg (dark)"},"composerPopoverBorder":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Composerpopoverborder","description":"Composer emoji-popover border (dark)"}},"type":"object","title":"DesignTokenColorsDark","description":"Per-mode DARK colour overrides (``designTokens.colorsDark``, Phase G).\n\nA sibling of ``DesignTokenColors`` holding the dark variant of every colour\nleaf that renders differently in dark mode. ABSENT ⇒ the widget renders\nexactly as it did before this group existed (the dark literal, or — for a\nleaf an org set in ``colors`` and that historically painted both modes — that\n``colors`` value). Only leaves with a genuine dark render path live here; a\nmode-invariant leaf (launcher, header gradient, send button, hero) has no\nentry, so no dead tokens are introduced.\n\nField names carry NO ``Dark`` suffix — the group is the mode. The 13 leaves\nthat previously lived as ``colors.<name>Dark`` twins were migrated here; the\nupconverter on ``DesignTokens`` lifts any legacy value so no row regresses."},"DesignTokenGeometry":{"properties":{"launcherSize":{"anyOf":[{"type":"string","maxLength":10},{"type":"null"}],"title":"Launchersize"},"launcherOffsetX":{"anyOf":[{"type":"string","maxLength":10},{"type":"null"}],"title":"Launcheroffsetx"},"launcherOffsetY":{"anyOf":[{"type":"string","maxLength":10},{"type":"null"}],"title":"Launcheroffsety"},"widgetHeight":{"anyOf":[{"type":"string","maxLength":10},{"type":"null"}],"title":"Widgetheight"},"widgetHeightExpanded":{"anyOf":[{"type":"string","maxLength":10},{"type":"null"}],"title":"Widgetheightexpanded"},"widgetWidthExpanded":{"anyOf":[{"type":"string","maxLength":10},{"type":"null"}],"title":"Widgetwidthexpanded"},"badgeSize":{"anyOf":[{"type":"string","maxLength":10},{"type":"null"}],"title":"Badgesize"},"chipGap":{"anyOf":[{"type":"string","maxLength":10},{"type":"null"}],"title":"Chipgap"}},"type":"object","title":"DesignTokenGeometry","description":"RFC Phase E4 — launcher / panel / badge / chip geometry, CLAMPED.\n\nThe most locked-down group in the model, because `chat-script` injects these\ninto the CUSTOMER's page rather than into the widget iframe (RFC §17.1).\nUnclamped geometry on a host page is a defacement vector, so every leaf is\nwhole-pixel-only and range-bounded — see `_require_px_in_range`.\n\nRanges for `launcherSize` / `launcherOffset*` are INHERITED from the ratified\nproduct decision (RFC §19 decision 4: \"launcher geometry in scope with\nclamped ranges — size ~36-64px, offsets ~8-48px\"), not invented here.\n\nWidget COLLAPSED WIDTH is deliberately absent: it is already plumbed as the\nflat `chatWidth` column and read at runtime by the deployed bundle, so a\ntoken would be a second writer for one property.\n\n── TWO CLAMPS ARE ONE-DIRECTIONAL (max pinned at today's value) ────────────\n`widgetWidthExpanded` (max 640) and `launcherOffsetX` (max 20) may only ever\nSHRINK. This is not conservatism, it is a live constraint:\n\nThe expanded panel needs a `widgetWidthExpanded + launcherOffsetX` viewport\nto fit, but the mobile veto that hides the expand control is the hardcoded\n`MOBILE_BREAKPOINT_PX = 560` (`chat-script/src/components/container.ts`,\nmirrored as a literal `@media (max-width: 560px)` in `styles.ts`). Today's\n640 + 20 = 660 already exceeds it, so viewports 561-659px ALREADY render an\noverflowing panel — a pre-existing defect (GH #12173). Letting either value\nGROW would widen that band onto more real devices.\n\nA media-query CONDITION cannot read a custom property, so the guard cannot be\nderived the way the panel's `bottom` is; correcting it means making\n`MOBILE_BREAKPOINT_PX` config-derived across `container.ts` + `expand.ts` +\nthe emitted media query. That is GH #12173, and it is what lifts these two\nceilings. Until it lands, 640 and 20 are load-bearing — do not raise them.\n\nTHE RULE, so it is applied correctly next time: an axis needs a\none-directional clamp exactly when it has NO viewport clamp. The horizontal\naxis has none. The vertical axis has `calc(100dvh - 140px)`, and the worst\ncase under these ranges is `launcherOffsetY(48) + launcherSize(64) + gap(11)\n= 123px`, which stays inside that 140px reserve with 17px to spare at every\nviewport height — which is why `launcherOffsetY`, `launcherSize`, `badgeSize`\nand `chipGap` are free to grow. Any future range change must preserve\n`launcherOffsetY + launcherSize + 11 <= 140`."},"DesignTokenHeader":{"properties":{"mode":{"anyOf":[{"type":"string","enum":["solid","gradient"]},{"type":"null"}],"title":"Mode"},"fromStop":{"anyOf":[{"type":"integer","maximum":100.0,"minimum":0.0},{"type":"null"}],"title":"Fromstop"},"angle":{"anyOf":[{"type":"integer","maximum":360.0,"minimum":0.0},{"type":"null"}],"title":"Angle"}},"type":"object","title":"DesignTokenHeader","description":"How the header surface is painted — mode + gradient blend point.\n\nA SEPARATE group, not new `DesignTokenColors` slots, and that is forced:\n`DesignTokenColors` hex-validates EVERY field (`@field_validator(\"*\")`), so a\n`\"solid\"` mode or a numeric stop there would 422 the whole save.\n\nBoth leaves are ABSENT by default and absence is meaningful — it means\n\"render exactly as this org rendered before this group existed\":\n\n* ``mode`` absent  -> gradient (today's only behaviour).\n* ``fromStop`` absent -> no interpolation hint is emitted at all, so the CSS\n  is byte-identical to the legacy string (see `buildWidgetCssVars`). The\n  50/50 default is therefore expressed as ABSENCE, never as a written 50 —\n  existing rows keep rendering without relying on hint-equivalence."},"DesignTokenInput":{"properties":{"background":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Background"},"borderColor":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bordercolor"},"focusBorderColor":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Focusbordercolor"}},"type":"object","title":"DesignTokenInput","description":"Composer input surface colors (hex-validated)."},"DesignTokenMotion":{"properties":{"duration":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Duration"},"easing":{"anyOf":[{"type":"string","maxLength":60},{"type":"null"}],"title":"Easing"}},"type":"object","title":"DesignTokenMotion","description":"Interaction motion — one duration (<time>) + one timing-function."},"DesignTokenRadius":{"properties":{"widget":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Widget"},"bubble":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Bubble"},"control":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Control"},"input":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Input"},"launcher":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Launcher"}},"type":"object","title":"DesignTokenRadius","description":"Border-radius slots (CSS dimensions; launcher is typically 50%)."},"DesignTokenShadows":{"properties":{"widget":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Widget"},"launcher":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Launcher"},"bubble":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Bubble"},"suggested":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Suggested"},"launcherHover":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Launcherhover"}},"type":"object","title":"DesignTokenShadows","description":"box-shadow slots — charset-restricted, see _require_css_shadow."},"DesignTokenSpacing":{"properties":{"bubblePadding":{"anyOf":[{"type":"string","maxLength":50},{"type":"null"}],"title":"Bubblepadding"},"sectionGap":{"anyOf":[{"type":"string","maxLength":50},{"type":"null"}],"title":"Sectiongap"}},"type":"object","title":"DesignTokenSpacing","description":"Spacing slots — padding shorthand (1-4 dims) and single-dim gaps."},"DesignTokenTransform":{"properties":{"launcherHover":{"anyOf":[{"type":"string","maxLength":10},{"type":"null"}],"title":"Launcherhover"},"launcherActive":{"anyOf":[{"type":"string","maxLength":10},{"type":"null"}],"title":"Launcheractive"},"chipHover":{"anyOf":[{"type":"string","maxLength":10},{"type":"null"}],"title":"Chiphover"},"chipActive":{"anyOf":[{"type":"string","maxLength":10},{"type":"null"}],"title":"Chipactive"},"windowEnter":{"anyOf":[{"type":"string","maxLength":10},{"type":"null"}],"title":"Windowenter"},"rippleFrom":{"anyOf":[{"type":"string","maxLength":10},{"type":"null"}],"title":"Ripplefrom"},"rippleTo":{"anyOf":[{"type":"string","maxLength":10},{"type":"null"}],"title":"Rippleto"}},"type":"object","title":"DesignTokenTransform","description":"RFC Phase E3 — interaction transform SCALES (unitless multipliers).\n\nMotion *timing* (duration + easing) already shipped as `DesignTokenMotion`;\nthis is the other half of E3. Every leaf is optional and absence means \"the\nliteral `chat-script/src/styles.ts` ships today\", so `transform` absent =\nbyte-identical rendering.\n\nEach leaf carries its OWN range because the ranges are semantic, not\ncosmetic: a \"grow\" interaction above ~1.2 reads as a glitch rather than\nfeedback, and a \"press\" interaction must stay at or below 1.0 or the element\ngrows when pushed.\n\nRotation is deliberately NOT here. RFC §16 scopes E3 to *scales*, and the\nlauncher's icon swap uses a ±90deg PAIR that must stay symmetric — one leaf\nwould invite an asymmetric swap, two would invite a broken one."},"DesignTokenTypography":{"properties":{"fontFamily":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Fontfamily"},"fontUrl":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Fonturl"},"headingWeight":{"anyOf":[{"type":"integer","maximum":1000.0,"minimum":100.0},{"type":"null"}],"title":"Headingweight"},"bodyWeight":{"anyOf":[{"type":"integer","maximum":1000.0,"minimum":100.0},{"type":"null"}],"title":"Bodyweight"},"fontSize":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Fontsize"},"lineHeight":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Lineheight"},"letterSpacing":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Letterspacing"}},"type":"object","title":"DesignTokenTypography","description":"Font family / weights. fontUrl is an optional CSS URL (Google Fonts css2)."},"DesignTokens":{"properties":{"version":{"type":"integer","title":"Version","default":1},"colors":{"anyOf":[{"$ref":"#/components/schemas/DesignTokenColors"},{"type":"null"}]},"colorsDark":{"anyOf":[{"$ref":"#/components/schemas/DesignTokenColorsDark"},{"type":"null"}]},"typography":{"anyOf":[{"$ref":"#/components/schemas/DesignTokenTypography"},{"type":"null"}]},"radius":{"anyOf":[{"$ref":"#/components/schemas/DesignTokenRadius"},{"type":"null"}]},"shadows":{"anyOf":[{"$ref":"#/components/schemas/DesignTokenShadows"},{"type":"null"}]},"motion":{"anyOf":[{"$ref":"#/components/schemas/DesignTokenMotion"},{"type":"null"}]},"transform":{"anyOf":[{"$ref":"#/components/schemas/DesignTokenTransform"},{"type":"null"}]},"input":{"anyOf":[{"$ref":"#/components/schemas/DesignTokenInput"},{"type":"null"}]},"badge":{"anyOf":[{"$ref":"#/components/schemas/DesignTokenBadge"},{"type":"null"}]},"spacing":{"anyOf":[{"$ref":"#/components/schemas/DesignTokenSpacing"},{"type":"null"}]},"geometry":{"anyOf":[{"$ref":"#/components/schemas/DesignTokenGeometry"},{"type":"null"}]},"header":{"anyOf":[{"$ref":"#/components/schemas/DesignTokenHeader"},{"type":"null"}]}},"type":"object","title":"DesignTokens","description":"Extended widget theme tokens stored in chat_widget_settings.designTokens.\n\nShape is the shared FE/BE contract — the TypeScript twin lives in\nfrontend/features/webchat/widget-preview/chat-design-settings.ts."},"DeskApprovalDecisionRequest":{"properties":{"decision":{"type":"string","enum":["approve","reject"],"title":"Decision"},"note":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Note","description":"Optional note. The engine records it as `notes` on an approval and `reason` on a rejection."}},"type":"object","required":["decision"],"title":"DeskApprovalDecisionRequest","description":"Approve or reject one paused workflow run.\n\n`decision` is CLOSED to the two values the engine accepts. A free string\nwould reach the engine and come back as a 502, which reads like an outage\nrather than a typo."},"DeskAskRequest":{"properties":{"question":{"type":"string","maxLength":2000,"minLength":1,"title":"Question"},"decision_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Decision Id","description":"Ground the answer in this decision card."},"deal_id":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Deal Id","description":"Ground the answer in this deal."}},"type":"object","required":["question"],"title":"DeskAskRequest","description":"A grounded question about a card or a deal.\n\nGive it something to ground on: with neither `decision_id` nor `deal_id`\nthe answer has no record to read and comes back generic."},"DeskAutonomyUpdate":{"properties":{"lanes":{"additionalProperties":{"type":"string"},"type":"object","title":"Lanes","description":"Map of decision_type -> lane (autopilot/approve/off)."},"autonomy_families":{"anyOf":[{"additionalProperties":{"type":"string"},"type":"object"},{"type":"null"}],"title":"Autonomy Families","description":"Map of lane family -> lane (plan_work/outreach/hygiene_and_alerts). Omit to leave family answers untouched; send `{}` to clear them."}},"type":"object","required":["lanes"],"title":"DeskAutonomyUpdate","description":"Which decisions the desk may act on WITHOUT asking the rep first.\n\nA lane of `autopilot` means the desk executes that decision type on the\nrep's behalf - including the ones that send. `approve` asks first, `off`\nstops the type being raised at all. The app validates both maps against its\nown `DecisionType` / `AutonomyLane` / lane-family vocabularies and answers\n400 on anything it could not act on, so this surface forwards them as open\nmaps rather than freezing a copy of three enums that move with the product.\n\nAn omitted `autonomy_families` means \"I did not touch the family\nquestions\", so a partial save cannot wipe them. An explicit `{}` clears\nthem and hands every type back to its own lane - the only way back once a\nfamily has been answered."},"DeskBatch":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"item_ids":{"items":{"type":"string"},"type":"array","title":"Item Ids"},"total":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Total"},"completed":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Completed"},"remaining":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Remaining"},"started_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Started At"},"completed_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Completed At"}},"additionalProperties":true,"type":"object","title":"DeskBatch","description":"Today's frozen batch.\n\nA batch is FINITE by design: the rep freezes a ranked slice of the queue so\nthe day has an end. `None` from the app means no batch has been started\ntoday, which is different from a batch with no items left - the response\nkeeps that distinction rather than flattening both to an empty batch."},"DeskBatchPullRequest":{"properties":{"item_ids":{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":40,"minItems":1,"title":"Item Ids","description":"Decision ids to append. 1-40 - a smaller cap than start, by design."},"tz_offset":{"type":"integer","maximum":840.0,"minimum":-840.0,"title":"Tz Offset","description":"The rep's UTC offset in minutes.","default":0}},"type":"object","required":["item_ids"],"title":"DeskBatchPullRequest","description":"Append newly selected cards to today's existing batch."},"DeskBatchStartRequest":{"properties":{"item_ids":{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":80,"minItems":1,"title":"Item Ids","description":"Decision ids to freeze into the batch. 1-80 - the cap is the app's."},"tz_offset":{"type":"integer","maximum":840.0,"minimum":-840.0,"title":"Tz Offset","description":"The rep's UTC offset in MINUTES (local = UTC + tz_offset). A batch is scoped to the rep's local day, so a wrong offset returns yesterday's batch or starts a second one.","default":0}},"type":"object","required":["item_ids"],"title":"DeskBatchStartRequest","description":"Freeze today's ranked queue into a finite batch.\n\n`item_ids` is typed `list[UUID]`, not `list[str]`, so a malformed id is a\nrequest-validation 422 that NAMES the offending element. Typed as strings,\nthe app's own `list[UUID]` model raises a pydantic `ValidationError` from\ninside the handler body instead - the same class of bare-500 the path\nguard exists to prevent, one layer in."},"DeskCardContext":{"properties":{"why":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Why","description":"The one-line reason, shown at the top of the card."},"persona":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Persona"},"facts":{"items":{"type":"string"},"type":"array","maxItems":20,"title":"Facts","description":"Bullets under what we know. Empty ones are dropped."},"fields":{"additionalProperties":{"type":"string"},"type":"object","maxProperties":40,"title":"Fields","description":"The columns the card was built from, shown as chips."}},"type":"object","title":"DeskCardContext"},"DeskCardCreateRequest":{"properties":{"owner_id":{"type":"string","maxLength":320,"minLength":1,"title":"Owner Id","description":"Whose desk: a team member's email, id or user id. With a personal key or an OAuth connection this must be the caller's own email (the key is a person; anyone else is 403 owner_not_self). Only an org or machine key may name another rep."},"contact_id":{"type":"integer","maximum":9.223372036854776e+18,"exclusiveMinimum":0.0,"title":"Contact Id","description":"The contact the touch is for."},"account_id":{"anyOf":[{"type":"integer","maximum":9.223372036854776e+18,"exclusiveMinimum":0.0},{"type":"null"}],"title":"Account Id","description":"The contact's company, when it is not the contact's own."},"channel":{"type":"string","maxLength":32,"minLength":1,"title":"Channel","description":"email, linkedin or call."},"due_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Due At","description":"When the touch is due. It orders the queue and never hides the card."},"priority":{"type":"string","maxLength":16,"title":"Priority","description":"low, normal, high or urgent.","default":"normal"},"list_id":{"anyOf":[{"type":"integer","maximum":9.223372036854776e+18,"exclusiveMinimum":0.0},{"type":"null"}],"title":"List Id"},"touch":{"anyOf":[{"type":"integer","maximum":1000.0,"minimum":1.0},{"type":"null"}],"title":"Touch","description":"The touch number in the list's cadence."},"external_key":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"External Key","description":"Your own key for this touch. Posting it again updates the unsent card. Keys are kept apart by `origin.kind`; with no `origin.kind` the key must be unique across the org."},"sender":{"anyOf":[{"$ref":"#/components/schemas/DeskCardSender"},{"type":"null"}]},"context":{"anyOf":[{"$ref":"#/components/schemas/DeskCardContext"},{"type":"null"}]},"draft":{"anyOf":[{"$ref":"#/components/schemas/DeskCardDraft"},{"type":"null"}]},"origin":{"anyOf":[{"$ref":"#/components/schemas/DeskCardOrigin"},{"type":"null"}]}},"type":"object","required":["owner_id","contact_id","channel"],"title":"DeskCardCreateRequest"},"DeskCardDraft":{"properties":{"subject":{"anyOf":[{"type":"string","maxLength":300},{"type":"null"}],"title":"Subject"},"body":{"anyOf":[{"type":"string","maxLength":20000},{"type":"null"}],"title":"Body"},"kind":{"anyOf":[{"type":"string","maxLength":32},{"type":"null"}],"title":"Kind"},"message":{"anyOf":[{"type":"string","maxLength":8000},{"type":"null"}],"title":"Message","description":"A connect note is at most 300 characters."},"talking_points":{"items":{"type":"string"},"type":"array","maxItems":20,"title":"Talking Points"},"questions":{"items":{"type":"string"},"type":"array","maxItems":20,"title":"Questions"},"handoff_line":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Handoff Line"}},"type":"object","title":"DeskCardDraft","description":"Shaped by the channel. email: subject, body. linkedin: kind (connect or\nmessage), message, a connect note at most 300 characters. call:\ntalking_points, questions, handoff_line."},"DeskCardOrigin":{"properties":{"kind":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Kind","description":"Who planned it, e.g. \"list_plan\" or \"workflow\"."},"mapping":{"anyOf":[{"type":"string","maxLength":300},{"type":"null"}],"title":"Mapping"}},"type":"object","title":"DeskCardOrigin"},"DeskCardResult":{"properties":{"card_id":{"type":"string","title":"Card Id"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"\"queued\" until the rep acts on it."},"due_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Due At"},"url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Url"},"updated":{"type":"boolean","title":"Updated","description":"True when this body updated a card already on the desk.","default":false},"note":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Note"}},"type":"object","required":["card_id"],"title":"DeskCardResult"},"DeskCardSender":{"properties":{"mailbox":{"anyOf":[{"type":"string","maxLength":320},{"type":"null"}],"title":"Mailbox","description":"Email address the card sends from. Checked against the rep's send rights when the rep sends."},"mailbox_id":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Mailbox Id","description":"Not used: email sends from `mailbox`, else the rep's own mailbox."},"linkedin_seat_id":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Linkedin Seat Id","description":"Not used: LinkedIn sends from the rep's own connected account."}},"type":"object","title":"DeskCardSender"},"DeskDecision":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"decision_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Decision Type","description":"What kind of action this card is asking for."},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"pending, approved, edited, skipped, deferred, snoozed, done_already."},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"summary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Summary"},"priority":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Priority"},"source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source","description":"Exact signal id, e.g. \"form_submitted\"."},"source_group":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Group","description":"Signal family, e.g. \"forms\"."},"entity_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Type"},"entity_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Id"},"snoozed_until":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Snoozed Until"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"resolved_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Resolved At"}},"additionalProperties":true,"type":"object","title":"DeskDecision","description":"One card in the queue: something the desk thinks a rep should do next."},"DeskDecisionListResponse":{"properties":{"decisions":{"items":{"$ref":"#/components/schemas/DeskDecision"},"type":"array","title":"Decisions"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"DeskDecisionListResponse","description":"A page of decision cards."},"DeskEmailImproveRequest":{"properties":{"subject":{"type":"string","maxLength":1000,"title":"Subject","default":""},"body":{"type":"string","maxLength":50000,"title":"Body"}},"type":"object","required":["body"],"title":"DeskEmailImproveRequest","description":"A draft to rewrite. The rewrite targets its FAILING subscores."},"DeskEmailScoreRequest":{"properties":{"subject":{"type":"string","maxLength":1000,"title":"Subject","default":""},"body":{"type":"string","maxLength":50000,"title":"Body"},"contact_name":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Contact Name","description":"Recipient name, used for the personalisation subscore."}},"type":"object","required":["body"],"title":"DeskEmailScoreRequest","description":"A draft to score 0-100. Heuristics plus an AI read."},"DeskLinkedInSenderUpdate":{"properties":{"provider_member_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Provider Member Id","description":"The LinkedIn account to claim. NULL releases the current claim."}},"type":"object","title":"DeskLinkedInSenderUpdate","description":"Claim a LinkedIn account for this rep, or give the claim up.\n\nNULL is the release, not a no-op. The claim is exclusive: two unique\nconstraints on the underlying table are what stop a rep taking a\ncolleague's account, so a claim on a held account is refused with a 409\nrather than silently reassigned."},"DeskListGoalUpdate":{"properties":{"audience_id":{"type":"integer","title":"Audience Id","description":"The dial list this target belongs to."},"target":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Target","description":"Dials per day. NULL CLEARS the target rather than setting zero."}},"type":"object","required":["audience_id"],"title":"DeskListGoalUpdate","description":"Set or clear one list's daily dial target."},"DeskListGroupOverrideUpdate":{"properties":{"overrides":{"additionalProperties":{"type":"string","enum":["form","warm","cold"]},"type":"object","title":"Overrides","description":"Dial-list id -> band (`form`, `warm` or `cold`). REPLACES every stored move."}},"type":"object","title":"DeskListGroupOverrideUpdate","description":"The rep's own moves of dial lists into a band. THE WHOLE MAP.\n\nKeyed by dial-list (audience) id. A PUT REPLACES what is stored rather\nthan merging one entry into it, so a list left out goes back to the band\nthe desk would have put it in, and `{}` clears every move."},"DeskListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"DeskListPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape."},"DeskListPriorityUpdate":{"properties":{"audience_ids":{"items":{"type":"integer"},"type":"array","title":"Audience Ids","description":"Dial-list (audience) ids, most important first. REPLACES the whole order - an empty list clears every pin."}},"type":"object","title":"DeskListPriorityUpdate","description":"The rep's dial-list order. THE WHOLE ORDER, most important first.\n\nNot a partial edit and not an append: the app replaces the stored order\nwith exactly this list, so a caller that sends one id has pinned one list\nand UNPINNED every other. Said here because the field name alone reads like\n\"add these\"."},"DeskOrgSettingsUpdate":{"properties":{"no_reply_threshold_days":{"anyOf":[{"type":"integer","maximum":60.0,"minimum":1.0},{"type":"null"}],"title":"No Reply Threshold Days"},"no_reply_channels":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":1},{"type":"null"}],"title":"No Reply Channels"},"enrichment_win_fields":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":9},{"type":"null"}],"title":"Enrichment Win Fields"},"max_cards_per_generator_per_day":{"anyOf":[{"type":"integer","maximum":500.0,"minimum":1.0},{"type":"null"}],"title":"Max Cards Per Generator Per Day"},"max_auto_account_plans_per_day":{"anyOf":[{"type":"integer","maximum":100.0,"minimum":0.0},{"type":"null"}],"title":"Max Auto Account Plans Per Day","description":"DAILY CAP on charged auto account plans."},"max_account_replans_per_day":{"anyOf":[{"type":"integer","maximum":100.0,"minimum":0.0},{"type":"null"}],"title":"Max Account Replans Per Day","description":"DAILY CAP on charged account re-plans."},"max_skill_plans_per_day":{"anyOf":[{"type":"integer","maximum":100.0,"minimum":0.0},{"type":"null"}],"title":"Max Skill Plans Per Day","description":"DAILY CAP on charged skill plans."},"plan_required_stage_ids":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":20},{"type":"null"}],"title":"Plan Required Stage Ids"},"signals_enabled":{"anyOf":[{"additionalProperties":{"type":"boolean"},"type":"object"},{"type":"null"}],"title":"Signals Enabled","description":"Per-signal kill switches. `ai_briefs` is the desk-wide LLM-spend gate and `morning_kickoff` gates the daily briefing."},"daily_action_target":{"anyOf":[{"type":"integer","maximum":200.0,"minimum":0.0},{"type":"null"}],"title":"Daily Action Target"},"pipeline_target_quarterly":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Pipeline Target Quarterly"},"lead_sla_minutes":{"anyOf":[{"type":"integer","maximum":240.0,"minimum":0.0},{"type":"null"}],"title":"Lead Sla Minutes"},"desk_writes_deal_plans":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Desk Writes Deal Plans"},"desk_acts_on_signals":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Desk Acts On Signals"},"desk_keeps_crm_tidy":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Desk Keeps Crm Tidy"},"desk_drafts_with_ai":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Desk Drafts With Ai"},"reps_may_fire_workflows":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Reps May Fire Workflows"},"desk_escalates_to_managers":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Desk Escalates To Managers"},"stalled_deal_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Stalled Deal Enabled"},"stalled_deal_stage_ids":{"anyOf":[{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":200},{"type":"null"}],"title":"Stalled Deal Stage Ids"},"stalled_deal_warn_after_days":{"anyOf":[{"type":"integer","maximum":60.0,"minimum":1.0},{"type":"null"}],"title":"Stalled Deal Warn After Days"},"stalled_deal_approve_after_days":{"anyOf":[{"type":"integer","maximum":60.0,"minimum":1.0},{"type":"null"}],"title":"Stalled Deal Approve After Days"},"stalled_deal_manager_user_id":{"anyOf":[{"type":"string","maxLength":320},{"type":"null"}],"title":"Stalled Deal Manager User Id"},"stalled_deal_fallback_manager_user_id":{"anyOf":[{"type":"string","maxLength":320},{"type":"null"}],"title":"Stalled Deal Fallback Manager User Id"},"stalled_deal_reassign_to_user_id":{"anyOf":[{"type":"string","maxLength":320},{"type":"null"}],"title":"Stalled Deal Reassign To User Id"},"stalled_deal_send_email":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Stalled Deal Send Email","description":"Let the stalled-deal escalation EMAIL the manager."},"stalled_deal_undo_window_minutes":{"anyOf":[{"type":"integer","maximum":1440.0,"minimum":0.0},{"type":"null"}],"title":"Stalled Deal Undo Window Minutes"},"stalled_deal_reminder_after_hours":{"anyOf":[{"type":"integer","maximum":168.0,"minimum":1.0},{"type":"null"}],"title":"Stalled Deal Reminder After Hours"},"stalled_deal_skip_crm_synced_transfer":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Stalled Deal Skip Crm Synced Transfer"},"stalled_deal_require_activity_evidence":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Stalled Deal Require Activity Evidence"},"stalled_deal_min_deal_age_days":{"anyOf":[{"type":"integer","maximum":365.0,"minimum":0.0},{"type":"null"}],"title":"Stalled Deal Min Deal Age Days"},"stalled_deal_min_amount":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Stalled Deal Min Amount"},"overdue_self_task_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Overdue Self Task Enabled"},"overdue_task_max_age_days":{"anyOf":[{"type":"integer","maximum":365.0,"minimum":0.0},{"type":"null"}],"title":"Overdue Task Max Age Days"},"contact_update_planned_deals_only":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Contact Update Planned Deals Only"},"fallback_owner_emails":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":20},{"type":"null"}],"title":"Fallback Owner Emails"},"signal_policies":{"anyOf":[{"additionalProperties":{"$ref":"#/components/schemas/DeskSignalPolicy"},"type":"object"},{"type":"null"}],"title":"Signal Policies"}},"type":"object","title":"DeskOrgSettingsUpdate","description":"Org-level desk settings. PARTIAL - an unset field is left untouched.\n\nMirrors `desk.interfaces.fastapi.dtos.DeskOrgSettingsUpdate` field for\nfield, pinned by test, because it is constructed inside the proxy.\n\nTHREE KINDS OF FIELD LIVE HERE AND THEY ARE NOT EQUALLY QUIET\n---------------------------------------------------------------\nMost are thresholds and ids. But `max_auto_account_plans_per_day`,\n`max_account_replans_per_day` and `max_skill_plans_per_day` are the org's\nDAILY SPEND CAPS on charged model calls, and `desk_acts_on_signals`,\n`desk_drafts_with_ai`, `desk_writes_deal_plans`, `reps_may_fire_workflows`\nand `stalled_deal_send_email` are the switches that let the desk act - and\nemail - on its own. That is why this operation is not tiered a plain\n`write`; see the router docstring.\n\nEvery value is validated by the app's own `validated_payload()` and\n`save_desk_org_settings`, which answer 400 with the reason. This surface\ndoes not second-guess either."},"DeskPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"DeskPayload","description":"An open envelope for one desk object.\n\nOpen on purpose - see the module docstring. A rebuilder gets every field\nthe desk returns, including ones added after this contract version."},"DeskResolveRequest":{"properties":{"status":{"type":"string","title":"Status","description":"approved, edited, skipped, deferred, snoozed or done_already. A status the app does not accept is a 400 rather than being silently dropped, which is why this is an open string and not an enum this surface would have to keep in lock-step. `done_already` resolves the card AND records the work on its entity."},"action_taken":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Action Taken","description":"Action payload, e.g. the edited email body."},"snoozed_until":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Snoozed Until","description":"REQUIRED when status=snoozed. Wake time, UTC."},"wake_condition":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Wake Condition","description":"Early-wake condition, valid only with status=snoozed: reply | site_visit | stage_change. `snoozed_until` stays required as the fallback timeout. `stage_change` is accepted but only wakes via that timeout today - no deal-stage-change event reaches the desk signal consumer yet."}},"type":"object","required":["status"],"title":"DeskResolveRequest","description":"Resolve a pending decision."},"DeskSendReplyRequest":{"properties":{"subject":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Subject"},"body":{"type":"string","minLength":1,"title":"Body","description":"The reply body. Reaches a real person."}},"type":"object","required":["body"],"title":"DeskSendReplyRequest","description":"The rep's reply, as it will arrive in the prospect's inbox.\n\nAn omitted `subject` keeps the thread's own. The opt-out check runs AGAIN\non send - `reply-target` already asked, but that answer is as old as the\nediting session and a STOP arriving while the rep typed must not be sent\nthrough."},"DeskSendSmsRequest":{"properties":{"body":{"type":"string","maxLength":1600,"minLength":1,"title":"Body","description":"The message. Reaches a real phone and costs carrier spend."}},"type":"object","required":["body"],"title":"DeskSendSmsRequest","description":"The rep's text, as it will arrive on the prospect's phone.\n\n1600 characters is the app's ceiling, not a display limit - it is the\nconcatenated-SMS cap, and a longer body is refused rather than truncated."},"DeskSignalPolicy":{"properties":{},"additionalProperties":true,"type":"object","title":"DeskSignalPolicy","description":"Per-signal policy override. Mirrors the app's `DeskSignalPolicyUpdate`.\n\nOpen (`extra=\"allow\"`) rather than pinned: this nests inside a JSONB\nsettings blob the desk extends per signal family, and a closed mirror would\nreject a key the app has just learned to read."},"DestinationCalendarEnvelope":{"properties":{"data":{"anyOf":[{"$ref":"#/components/schemas/DestinationCalendarResponse"},{"type":"null"}]}},"type":"object","title":"DestinationCalendarEnvelope","description":"Envelope for GET/PUT /calendars/destination. ``data`` is ``null`` when\nno destination calendar is configured."},"DestinationCalendarResponse":{"properties":{"id":{"type":"integer","title":"Id"},"integration":{"type":"string","title":"Integration"},"external_id":{"type":"string","title":"External Id"},"credential_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Credential Id"},"event_type_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Event Type Id"},"primary_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Primary Email"}},"type":"object","required":["id","integration","external_id"],"title":"DestinationCalendarResponse"},"DialContact":{"properties":{"contact_id":{"type":"string","title":"Contact Id"},"to_phone":{"type":"string","title":"To Phone"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"},"company":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"timezone":{"type":"string","title":"Timezone","default":"America/New_York"},"default_region":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Default Region"},"all_phones":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"All Phones"},"phone_index":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Phone Index"},"dynamic_columns":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Dynamic Columns"},"is_redial":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Redial","default":false},"redial_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Redial Count","default":0},"original_call_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Original Call Id"}},"type":"object","required":["contact_id","to_phone"],"title":"DialContact","description":"One person to call. `to_phone` is a REAL phone number of a REAL human.\n\nAn unparseable number is SKIPPED rather than rejecting the batch, so read\nthe response to learn who was actually dialed."},"DialerAgentSummary":{"properties":{"agent_id":{"type":"string","title":"Agent Id","description":"Agent UUID - feed this into create_dialer_session."},"agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent Name"},"role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Role"},"agent_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent Status"},"entity_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Type"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone"},"is_template":{"type":"boolean","title":"Is Template","default":false}},"type":"object","required":["agent_id"],"title":"DialerAgentSummary","description":"One row from the agents list.\n\nTrimmed to the fields a chat picker needs (name, role, status, and the\nUUID to feed back into ``create_dialer_session``). Anything else the\nvoice service returns (knowledge collections, voice/calendar) stays\nserver-side - the chat layer doesn't need it for the picker UX."},"DialerAgentsListResponse":{"properties":{"agents":{"items":{"$ref":"#/components/schemas/DialerAgentSummary"},"type":"array","title":"Agents"},"total_count":{"type":"integer","title":"Total Count","default":0}},"type":"object","title":"DialerAgentsListResponse","description":"List wrapper for the agents picker."},"DialerAnalyticsMeta":{"properties":{"org_id":{"type":"string","title":"Org Id"},"cached":{"type":"boolean","title":"Cached"},"timestamp":{"type":"string","format":"date-time","title":"Timestamp"},"query_time_ms":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Query Time Ms"},"degraded":{"type":"boolean","title":"Degraded","default":false},"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason"}},"type":"object","required":["org_id","cached","timestamp"],"title":"DialerAnalyticsMeta","description":"Metadata for dialer analytics responses."},"DialerAnalyticsResponse":{"properties":{"success":{"type":"boolean","title":"Success","default":true},"data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"items":{},"type":"array"}],"title":"Data"},"meta":{"$ref":"#/components/schemas/DialerAnalyticsMeta"}},"type":"object","required":["data","meta"],"title":"DialerAnalyticsResponse","description":"Standard dialer analytics response wrapper."},"DialerCallbackRequest":{"properties":{"success":{"type":"boolean","title":"Success","description":"True if the call connected and the contact should advance to the next step; false records an unsuccessful attempt."}},"type":"object","required":["success"],"title":"DialerCallbackRequest","description":"The outcome of a dialer call. Mirrors `DialerCallbackPayload`."},"DialerListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"DialerListPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape."},"DialerNumberInfo":{"properties":{"number":{"type":"string","title":"Number"},"inbound_type":{"type":"string","title":"Inbound Type","default":"ai"},"telephony_provider":{"type":"string","title":"Telephony Provider","default":"twilio"},"calls_today":{"type":"integer","title":"Calls Today","default":0},"calls_7d":{"type":"integer","title":"Calls 7D","default":0},"connect_rate_7d":{"type":"number","title":"Connect Rate 7D","default":0.0},"is_valid":{"type":"boolean","title":"Is Valid","default":true},"daily_limit":{"type":"integer","title":"Daily Limit","default":40},"assigned_to":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Assigned To"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"}},"type":"object","required":["number"],"title":"DialerNumberInfo","description":"One available dialer number with its current health stats."},"DialerNumbersListResponse":{"properties":{"numbers":{"items":{"$ref":"#/components/schemas/DialerNumberInfo"},"type":"array","title":"Numbers"}},"type":"object","title":"DialerNumbersListResponse","description":"List wrapper for dialer numbers.\n\nThe voice payload includes a top-level ``daily_limit`` default; we\ndrop it from the public shape because it is per-number on each row\nalready, so re-publishing it would just confuse callers."},"DialerOrgSettingsRequest":{"properties":{"auto_disposition_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Auto Disposition Enabled","description":"Suggest a disposition from the call transcript after a connected call."},"live_coach_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Live Coach Enabled","description":"Live AI coach in the dialer drawer during calls. Sends call audio text to a model provider."},"live_coach_stt_mode":{"anyOf":[{"type":"string","enum":["off","shadow","primary"]},{"type":"null"}],"title":"Live Coach Stt Mode","description":"Live transcription source: off (Twilio), shadow (Twilio plus a comparison), primary."},"auto_disposition_mode":{"anyOf":[{"type":"string","enum":["off","phone","phone_jev"]},{"type":"null"}],"title":"Auto Disposition Mode","description":"Automatic outcome logging: off, phone (telephony outcomes) or phone_jev (plus suggestions)."},"auto_disposition_threshold":{"anyOf":[{"type":"number","maximum":0.95,"minimum":0.2},{"type":"null"}],"title":"Auto Disposition Threshold","description":"Kept for older clients; no longer gates a write."}},"type":"object","title":"DialerOrgSettingsRequest","description":"Partial update of the organisation's dialer settings: only the fields sent change."},"DialerPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"DialerPayload","description":"An open envelope for one dialer result.\n\nOpen because voice owns the shape of a session, a call stub and a queue\nstat, and it grows them without a contract bump here. A dropped field\nwould otherwise turn an added upstream field into a removed public one."},"DialerPreferencesRequest":{"properties":{"user_email":{"type":"string","title":"User Email"},"call_dnc_contacts":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Call Dnc Contacts"},"skip_voicemails":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Skip Voicemails"},"auto_rotate_numbers":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Auto Rotate Numbers"},"parallel_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Parallel Count"}},"type":"object","required":["user_email"],"title":"DialerPreferencesRequest","description":"Mirrors `UserPreferencesRequest` minus `org_id`.\n\n`call_dnc_contacts` decides whether the dialer will call numbers on a\ndo-not-call list. It is a compliance switch, not a convenience one."},"DialerReportFilters":{"properties":{"session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Id"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email"},"org_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Org Id"},"date_from":{"anyOf":[{},{"type":"null"}],"title":"Date From"},"date_to":{"anyOf":[{},{"type":"null"}],"title":"Date To"},"aggregation":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Aggregation"}},"type":"object","title":"DialerReportFilters","description":"Echo of the filters the voice service ran the report with.\n\nUseful for clients that need to confirm which slice they got back,\nespecially when the request omits ``date_from`` / ``date_to`` and the\nserver applies defaults."},"DialerReportMetric":{"properties":{"date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Date"},"sdr_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sdr Name"},"org_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Org Id"},"list_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"List Title"},"total_dials":{"type":"integer","title":"Total Dials","default":0},"total_connections":{"type":"integer","title":"Total Connections","default":0},"connection_rate":{"type":"number","title":"Connection Rate","default":0.0},"total_voicemails":{"type":"integer","title":"Total Voicemails","default":0},"voicemail_rate":{"type":"number","title":"Voicemail Rate","default":0.0},"talk_time_minutes":{"type":"number","title":"Talk Time Minutes","default":0.0},"avg_call_duration_minutes":{"type":"number","title":"Avg Call Duration Minutes","default":0.0},"dispositions":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Dispositions"},"success_rate":{"type":"number","title":"Success Rate","default":0.0},"unique_sessions":{"type":"integer","title":"Unique Sessions","default":0},"avg_calls_per_session":{"type":"number","title":"Avg Calls Per Session","default":0.0},"redial_count":{"type":"integer","title":"Redial Count","default":0},"redial_success_rate":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Redial Success Rate"},"peak_calling_hour":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Peak Calling Hour"},"total_callbacks":{"type":"integer","title":"Total Callbacks","default":0}},"type":"object","title":"DialerReportMetric","description":"One aggregated row in the analytics report.\n\nSchema mirrors ``ParallelDialerMetrics``. The disposition breakdown\nis a passthrough dict so that voice-side disposition additions do\nnot require a coordinated DTO bump here."},"DialerSessionCreateRequest":{"properties":{"name":{"type":"string","maxLength":200,"minLength":1,"title":"Name","description":"Session display name."},"from_phone":{"type":"string","maxLength":16,"minLength":9,"title":"From Phone","description":"Caller-ID phone number. Must be one of the org's dialer numbers."},"list_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"List Id","description":"Contact list ID the SDR will dial from. Stored in session metadata."},"list_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"List Title","description":"Display title for the list (e.g. 'Q4 ICP'). Stored in metadata."},"agent_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent Id","description":"Voice agent UUID. Use GET /voice/dialer/agents to look up."},"agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent Name","description":"Legacy V1 agent name fallback (defaults to \"default_agent\" upstream)."},"entity_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Type","description":"V2 agent entity type (\"agent\" or \"twin\"). Optional."},"studio_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Studio Campaign Id","description":"Campaign Builder (Studio) campaign UUID. Optional linkage."},"user_timezone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Timezone","description":"IANA timezone for analytics grouping (e.g. \"America/New_York\")."},"skip_voicemails":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Skip Voicemails","description":"Per-session override for voicemail-skip behaviour. None = use SDR default."},"parallel_count":{"anyOf":[{"type":"integer","maximum":5.0,"minimum":1.0},{"type":"null"}],"title":"Parallel Count","description":"Legs to dial per batch once the SDR opens the dialer UI (1 = power mode, 2-5 = parallel). None keeps voice's own default (2). Bug fix (graph8-com/g8 dev-API voice parity): this field previously had no effect - it was accepted by neither this DTO nor the upstream call, so any value a caller sent was silently dropped rather than forwarded."},"dialing_mode":{"anyOf":[{"type":"string","enum":["power","parallel"]},{"type":"null"}],"title":"Dialing Mode","description":"Override the session's dialing mode. None keeps voice's default ('power'). Same bug-fix note as parallel_count above - now forwarded instead of dropped."}},"type":"object","required":["name","from_phone"],"title":"DialerSessionCreateRequest","description":"Body for creating a parallel-dialer session in PAUSED state.\n\nThe session is created paused so the SDR can open the dialer UI and\nstart dialing on their own time. Org and user are pinned server-side\nfrom the API key - any value supplied here is ignored.\n\nRequired: ``name``, ``from_phone``.\nOptional: ``list_id`` / ``list_title`` (carried in session metadata),\n``agent_id`` (V2 agent UUID - use ``GET /voice/dialer/agents`` to look up),\n``studio_campaign_id`` (Campaign Builder UUID for studio campaign linkage)."},"DialerSessionCreateResponse":{"properties":{"session_id":{"type":"string","title":"Session Id"},"status":{"type":"string","title":"Status"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"org_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Org Id"},"user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Id"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email"},"from_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"From Phone"},"session_metadata":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Session Metadata"},"total_calls":{"type":"integer","title":"Total Calls","default":0},"created_at":{"anyOf":[{},{"type":"null"}],"title":"Created At"},"message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Message"}},"type":"object","required":["session_id","status"],"title":"DialerSessionCreateResponse","description":"Echo of the voice service's ``ParallelDialResponse`` for a paused-create.\n\nWe deliberately drop ``twilio_token`` from the public shape - it is\nSDR-frontend-specific and is regenerated by the dialer UI on join, so\nre-publishing it here would only confuse a chat caller."},"DialerSessionResumeRequest":{"properties":{"max_contacts":{"type":"integer","maximum":4.0,"minimum":1.0,"title":"Max Contacts","description":"Number of contacts to dial in this batch. Voice caps parallel dialing at 4.","default":4}},"type":"object","title":"DialerSessionResumeRequest","description":"Body for resuming a paused parallel-dialer session.\n\nThe resume endpoint mirrors what the dialer UI does when the SDR\nclicks \"Start Dialing\" on a paused session: it pages the source list\nusing the cursor stored in ``session_metadata``, filters out\nalready-called contacts, and forwards the next batch to the voice\nservice's ``start-session`` endpoint.\n\nOnly ``max_contacts`` is exposed - org / user / from_phone /\nlist_id / agent / session_metadata are all read off the persisted\nsession so the caller doesn't have to reconstruct them."},"DialerSessionResumeResponse":{"properties":{"session_id":{"type":"string","title":"Session Id"},"status":{"type":"string","title":"Status"},"message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Message"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"org_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Org Id"},"user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Id"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email"},"from_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"From Phone"},"session_metadata":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Session Metadata"},"total_calls":{"type":"integer","title":"Total Calls","default":0},"dialed_count":{"type":"integer","title":"Dialed Count","default":0},"created_at":{"anyOf":[{},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["session_id","status"],"title":"DialerSessionResumeResponse","description":"Echo of voice's ``ParallelDialResponse`` plus a count of contacts dialed.\n\n``dialed_count`` is the number of calls actually placed in this\nresume batch. It can be lower than ``max_contacts`` when the list is\nnear exhausted, every remaining row is missing a phone, or every\ncandidate was already called earlier in the session.\n\n``twilio_token`` and ``conference_name`` are deliberately dropped -\nthey are SDR-frontend specific and an MCP / API caller has no use\nfor them. The dialer UI regenerates them on join."},"DialerSessionStatusUpdateRequest":{"properties":{"status":{"type":"string","title":"Status","description":"One of \"ACTIVE\" (resume), \"PAUSED\" (pause), \"COMPLETED\" (stop)."}},"type":"object","required":["status"],"title":"DialerSessionStatusUpdateRequest","description":"Body for pause / resume / stop on a parallel-dialer session.\n\nThe voice service treats a status PATCH as the lifecycle hook:\n- ``ACTIVE`` resumes a paused session.\n- ``PAUSED`` pauses an active session.\n- ``COMPLETED`` ends the session - one-way, can be re-opened only via\n  ``manual-dial`` (which we do not expose here).\n- ``FAILED`` is reserved for system use; we reject it on the public\n  surface so a caller cannot mis-mark a session."},"DialerSessionStatusUpdateResponse":{"properties":{"session_id":{"type":"string","title":"Session Id"},"status":{"type":"string","title":"Status"},"message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Message"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"org_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Org Id"},"user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Id"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email"},"from_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"From Phone"},"session_metadata":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Session Metadata"},"total_calls":{"type":"integer","title":"Total Calls","default":0},"created_at":{"anyOf":[{},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["session_id","status"],"title":"DialerSessionStatusUpdateResponse","description":"Echo of voice's ``SessionUpdateResponse`` for the public surface."},"DialerSessionSummary":{"properties":{"session_id":{"type":"string","title":"Session Id"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Id"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email"},"org_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Org Id"},"from_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"From Phone"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id"},"campaign_builder_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Builder Campaign Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"session_metadata":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Session Metadata"},"total_calls":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Total Calls"},"created_at":{"anyOf":[{},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{},{"type":"null"}],"title":"Updated At"},"contact_ids":{"items":{},"type":"array","title":"Contact Ids"}},"type":"object","required":["session_id"],"title":"DialerSessionSummary","description":"One row from the dialer-sessions list.\n\nThe voice service returns a flat dict per session built from\n``ParallelDialSession`` columns plus an aggregated ``contact_ids``\narray. We surface every documented column directly so that read-only\nconsumers can introspect a session without a follow-up call."},"DialerSessionsListResponse":{"properties":{"sessions":{"items":{"$ref":"#/components/schemas/DialerSessionSummary"},"type":"array","title":"Sessions"},"pagination":{"$ref":"#/components/schemas/VoicePagination"}},"type":"object","title":"DialerSessionsListResponse","description":"List wrapper for dialer sessions.\n\nTop-level matches the voice payload (``data`` + ``pagination``) so the\npublic API caller sees the exact same shape they would get if voice\nwere exposed directly. The standard ``ApiResponse`` envelope wraps\nTHIS object as its ``data`` field."},"DialerSettingsUpdate":{"properties":{"user_email":{"type":"string","minLength":3,"title":"User Email","description":"The rep whose settings these are."},"skip_voicemails":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Skip Voicemails"},"skip_dial_trees":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Skip Dial Trees"},"voicemail_grace_period":{"anyOf":[{"type":"integer","maximum":3.0,"minimum":1.0},{"type":"null"}],"title":"Voicemail Grace Period"},"dialing_mode":{"anyOf":[{"type":"string","enum":["power","parallel"]},{"type":"null"}],"title":"Dialing Mode"},"parallel_count":{"anyOf":[{"type":"integer","maximum":5.0,"minimum":2.0},{"type":"null"}],"title":"Parallel Count"},"dnd_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Dnd Enabled"}},"type":"object","required":["user_email"],"title":"DialerSettingsUpdate","description":"voice `DialerSettingsRequest`, without `org_id`. Only fields sent change."},"DialerStatsResponse":{"properties":{"filters":{"$ref":"#/components/schemas/DialerReportFilters"},"metrics":{"items":{"$ref":"#/components/schemas/DialerReportMetric"},"type":"array","title":"Metrics"},"summary":{"anyOf":[{"$ref":"#/components/schemas/DialerReportMetric"},{"type":"null"}]}},"type":"object","title":"DialerStatsResponse","description":"Top-level wrapper for dialer analytics.\n\nField names follow the voice ``ParallelDialerReport`` shape so the\nstructured response is meaningful both to a Developer API caller and\nto an MCP agent rendering it inline."},"DiscoverFieldsRequest":{"properties":{"source_column_id":{"type":"integer","title":"Source Column Id","description":"The raw JSON column to scan."},"sample_size":{"type":"integer","maximum":1000.0,"minimum":1.0,"title":"Sample Size","description":"Rows to sample.","default":100}},"type":"object","required":["source_column_id"],"title":"DiscoverFieldsRequest","description":"Sample a raw JSON column and report the field paths inside it."},"DiscoveryAnswerRequest":{"properties":{"field_key":{"type":"string","title":"Field Key","description":"Which discovery field this answers."},"value":{"title":"Value","description":"The answer. Shape depends on the field."},"grade":{"type":"string","title":"Grade","description":"Confidence in the answer: `green` (certain), `amber` (a working assumption) or `red` (a guess). Amber and red answers come back in `coverage.amber_fields` so they can be revisited."},"source":{"type":"string","title":"Source","description":"Who supplied it. Defaults to `user`.","default":"user"},"move_number":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Move Number","description":"Interview move this answers."},"session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Id","description":"Canvas session to report into."}},"type":"object","required":["field_key","grade"],"title":"DiscoveryAnswerRequest","description":"Mirror of `DiscoveryAnswerRequest`.\n\n`grade` is the customer's own confidence in the answer and it is REQUIRED\non the app model - it has no default there, so omitting it would raise\ninside the proxy rather than 422 here."},"DiscoveryRatifyRequest":{"properties":{"edits":{"additionalProperties":true,"type":"object","title":"Edits","description":"Field key -> corrected value, for answers the agent got wrong."},"confirmed":{"items":{"type":"string"},"type":"array","title":"Confirmed","description":"Field keys the customer accepts as the agent inferred them."},"session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Id","description":"Canvas session to report the ratification into."}},"type":"object","title":"DiscoveryRatifyRequest","description":"Mirror of `DiscoveryRatifyRequest`.\n\nBoth collections default to empty, matching the app: ratifying nothing is a\nlegal no-op rather than a 422, which is what makes the call safe to retry."},"DiscoveryTurnRequest":{"properties":{"message":{"type":"string","maxLength":8000,"minLength":1,"title":"Message"},"session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Id","description":"Canvas session to report into."}},"type":"object","required":["message"],"title":"DiscoveryTurnRequest","description":"Mirror of `DiscoveryTurnRequest`.\n\nThere is deliberately NO `history` field, and that is load-bearing rather\nthan an omission. The app removed one: the panel used to keep the\ntranscript in browser state and ship it back on every turn, so a reload\ndestroyed the customer's whole kickoff. The server re-grounds from the\ndurable record instead. A caller-supplied transcript is not something the\nserver can verify, and accepting one here would re-open exactly that hole."},"DisputeInvoiceRequest":{"properties":{"reason":{"type":"string","title":"Reason"}},"type":"object","required":["reason"],"title":"DisputeInvoiceRequest"},"DnsRecordsRequest":{"properties":{"records":{"additionalProperties":{"items":{"additionalProperties":true,"type":"object"},"type":"array"},"type":"object","title":"Records","description":"DNS records by type, e.g. {'TXT': [...], 'MX': [...], 'CNAME': [...]}"},"reset_to_default":{"type":"boolean","title":"Reset To Default","description":"Discard `records` and (re)apply graph8's default sending DNS zone","default":false}},"type":"object","title":"DnsRecordsRequest","description":"Set the sending DNS records (SPF/DKIM/MX/tracking CNAME) for a domain."},"DocSettingsUpdateRequest":{"properties":{"default_doc_ids":{"items":{"type":"string"},"type":"array","title":"Default Doc Ids","description":"Document type ids generated by default for this scope."},"mandatory_doc_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Mandatory Doc Ids","description":"Document type ids a user cannot uncheck. Omit to leave the current set unchanged; send an empty list to clear it."}},"type":"object","required":["default_doc_ids"],"title":"DocSettingsUpdateRequest","description":"Mirrors `UpdateDocSettingsRequest`.\n\n`mandatory_doc_ids` omitted means LEAVE THE CURRENT MANDATORY SET ALONE.\nSending `[]` CLEARS it. The two are different instructions and only one is\ndestructive."},"DocumentDraftAcceptRequest":{"properties":{"section_keys":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Section Keys"}},"type":"object","title":"DocumentDraftAcceptRequest","description":"Which sections of the draft to apply (default: every section)."},"DocumentFeedbackRequest":{"properties":{"feedback_type":{"type":"string","enum":["up","down"],"title":"Feedback Type","description":"Thumbs up or thumbs down on the document."},"usage_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Usage Id","description":"The usage record this feedback is about, when the feedback follows a specific use of the document rather than the document itself."}},"type":"object","required":["feedback_type"],"title":"DocumentFeedbackRequest","description":"Mirrors `campaign_builder.routers.global_context.FeedbackRequest`.\n\n`feedback_type` is a Literal where the app takes `str` and rejects anything\nbut `up`/`down` from inside the handler."},"DocumentListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"DocumentListPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape.\n\n`items` is always present and always the list, whichever key the app used\nfor it - so a caller can page one way rather than learning six key names."},"DocumentPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"DocumentPayload","description":"An open envelope for one document, folder or questionnaire.\n\nOpen on purpose: a Library document carries extraction metadata, a\nquestionnaire carries per-provider processing detail, and a generated deal\ndocument carries `structured_data` and `highlights` whose shape is the\ngenerator's rather than this contract's. Pinning those would silently drop\nwhatever the app learned to return that this file had not caught up on."},"DocumentPriorityUpdateRequest":{"properties":{"default_upload_priority":{"type":"string","enum":["high","medium","low"],"title":"Default Upload Priority","description":"Priority assigned to user-uploaded documents.","default":"high"},"default_generated_priority":{"type":"string","enum":["high","medium","low"],"title":"Default Generated Priority","description":"Priority assigned to AI-generated documents.","default":"medium"}},"type":"object","title":"DocumentPriorityUpdateRequest","description":"Mirrors `UpdateDocumentPrioritySettingsRequest`.\n\nBoth fields have defaults, so a partial body silently RESETS the field you\nleft out to the product default rather than leaving it alone. Send both."},"DocumentRevertRequest":{"properties":{"change_summary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Change Summary"}},"type":"object","title":"DocumentRevertRequest","description":"Optional note recorded on the revert's own version."},"DocumentRevisionRequest":{"properties":{"instruction":{"type":"string","maxLength":4000,"minLength":3,"title":"Instruction"}},"type":"object","required":["instruction"],"title":"DocumentRevisionRequest","description":"The instruction for the AI rewrite of one global-context document."},"DomainAvailabilityCheckRequest":{"properties":{"domain":{"type":"string","title":"Domain","description":"Domain to check, e.g. acme-outreach.com"},"provider":{"type":"string","enum":["registrar","managed"],"title":"Provider","description":"Provisioning path to check availability/price against.","default":"registrar"}},"type":"object","required":["domain"],"title":"DomainAvailabilityCheckRequest","description":"Check whether a domain can be bought, and its price. Spends no credits."},"DomainConfirmationRequest":{"properties":{"session_id":{"type":"string","title":"Session Id","description":"The proactive-setup canvas session id."},"card_id":{"type":"string","title":"Card Id","description":"The `domain_confirmation` card id."},"confirmed":{"type":"boolean","title":"Confirmed","description":"True = the pre-filled domain is correct as it stands."},"domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain","description":"The corrected company domain. REQUIRED when `confirmed` is false; ignored when it is true."}},"type":"object","required":["session_id","card_id","confirmed"],"title":"DomainConfirmationRequest","description":"Mirror of `DomainResponseRequest`."},"DomainForwardingRequest":{"properties":{"attributes":{"additionalProperties":true,"type":"object","title":"Attributes","description":"Forwarding attributes accepted by the registrar"}},"type":"object","required":["attributes"],"title":"DomainForwardingRequest","description":"Forward mail arriving at this domain somewhere else."},"DomainMailboxRefRequest":{"properties":{"mailbox_id":{"type":"integer","exclusiveMinimum":0.0,"title":"Mailbox Id","description":"Mailbox id (mailboxes.id) on this domain"}},"type":"object","required":["mailbox_id"],"title":"DomainMailboxRefRequest","description":"Names one mailbox on the domain in the path.\n\nShared by the info / TOTP / delete / status routes, all of which read\n``request[\"mailbox_id\"]`` off an untyped dict in the app."},"DomainNameGenerateRequest":{"properties":{"keyword":{"type":"string","title":"Keyword","description":"Seed word the generated names are built around, e.g. 'acme'"},"count":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Count","description":"How many suggestions to return","default":5},"prefixes":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Prefixes","description":"Comma-separated prefixes to try, e.g. 'get,try'"},"suffixes":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Suffixes","description":"Comma-separated suffixes to try, e.g. 'hq,mail'"},"provider":{"type":"string","enum":["registrar","managed","pilot"],"title":"Provider","description":"Provisioning path to generate for","default":"registrar"}},"type":"object","required":["keyword"],"title":"DomainNameGenerateRequest","description":"Suggest buyable domain names around a keyword. SPENDS NOTHING."},"DomainPurchaseRequest":{"properties":{"domains":{"items":{"type":"string"},"type":"array","maxItems":50,"title":"Domains","description":"Domains to buy, e.g. ['acme-outreach.com']. Up to 50 per request."},"spare_domains":{"items":{"type":"string"},"type":"array","maxItems":50,"title":"Spare Domains","description":"Extra domains bought as spare warm-up capacity (warm from day 0, excluded from sending until promoted). Up to 50 per request."},"period":{"type":"integer","minimum":1.0,"title":"Period","description":"Registration period, in years","default":1},"contact_info":{"additionalProperties":{"type":"string"},"type":"object","title":"Contact Info","description":"Registrant contact used for domain registration"},"provider":{"type":"string","enum":["registrar","managed","pilot"],"title":"Provider","description":"Provisioning path. 'pilot' is limited to allowlisted orgs and otherwise returns 400.","default":"registrar"}},"type":"object","required":["domains","contact_info"],"title":"DomainPurchaseRequest","description":"Buy one or more sending domains. Spends real credits — see the 402 contract\non the route docstring."},"DomainResponse":{"properties":{"domain_id":{"type":"string","title":"Domain Id"},"app_id":{"type":"string","title":"App Id"},"hostname":{"type":"string","title":"Hostname","description":"The canonical, normalized form -- not necessarily what was submitted."},"status":{"type":"string","title":"Status"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"verified_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Verified At"}},"type":"object","required":["domain_id","app_id","hostname","status"],"title":"DomainResponse"},"DomainTransferAvailabilityRequest":{"properties":{"domain":{"type":"string","title":"Domain","description":"Domain to check, e.g. acme-outreach.com"}},"type":"object","required":["domain"],"title":"DomainTransferAvailabilityRequest","description":"Check whether a domain you own elsewhere can be transferred in. SPENDS NOTHING."},"DomainTransferCancelRequest":{"properties":{"domain_id":{"type":"integer","exclusiveMinimum":0.0,"title":"Domain Id","description":"Provider domain id whose transfer should be aborted"}},"type":"object","required":["domain_id"],"title":"DomainTransferCancelRequest","description":"Abort an in-flight transfer.\n\nThe app handler reads ``request[\"domain_id\"]`` off an untyped dict, so a\nmissing key is a 500 there. Typed here, it is a 422."},"DomainTransferRequest":{"properties":{"domain":{"type":"string","title":"Domain","description":"Domain to transfer in, e.g. acme-outreach.com"},"auth_info":{"type":"string","title":"Auth Info","description":"Transfer authorisation code from your current registrar"},"contact_info":{"additionalProperties":{"type":"string"},"type":"object","title":"Contact Info","description":"Registrant contact recorded with the registrar"}},"type":"object","required":["domain","auth_info","contact_info"],"title":"DomainTransferRequest","description":"Transfer a domain you already own INTO graph8. SPENDS REAL MONEY."},"DomainVerificationInstructions":{"properties":{"domain":{"$ref":"#/components/schemas/DomainResponse"},"record_type":{"type":"string","title":"Record Type","default":"TXT"},"record_name":{"type":"string","title":"Record Name","description":"Create the record at this name, e.g. _graph8-challenge.app.example.com"},"record_value":{"type":"string","title":"Record Value"}},"type":"object","required":["domain","record_name","record_value"],"title":"DomainVerificationInstructions","description":"Everything the builder needs to prove control, and nothing else.\n\nThe token is returned ONLY here, at claim time. It is also stored, but there\nis deliberately no route that reads it back: a token readable on demand is a\ntoken an attacker with a stolen read-only key can harvest for every pending\ndomain on the platform."},"DraftEmailRequest":{"properties":{"contact_id":{"type":"integer","title":"Contact Id"},"contact_work_email":{"type":"string","title":"Contact Work Email"},"first_name":{"type":"string","title":"First Name"},"last_name":{"type":"string","title":"Last Name"},"instructions":{"type":"string","title":"Instructions","description":"What the email should do - the step's prompt."},"lead_info":{"type":"string","title":"Lead Info","description":"What is known about the contact, as free text."},"agent_name":{"type":"string","title":"Agent Name","description":"The textual agent whose voice and context are used."},"sequence_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Id","description":"Draft in the context of this sequence's linked campaign."},"studio_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Studio Campaign Id","description":"Draft in this campaign's context; wins over `sequence_id`."},"step_order":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Step Order"},"provider":{"anyOf":[{"type":"string","enum":["openai","anthropic","openrouter"]},{"type":"null"}],"title":"Provider","description":"Model provider, from `GET /sequencer/content/email/models`."},"model":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Model","description":"Model slug, from `GET /sequencer/content/email/models`."}},"type":"object","required":["contact_id","contact_work_email","first_name","last_name","instructions","lead_info","agent_name"],"title":"DraftEmailRequest","description":"Draft one contact's email. Mirrors `OnDemandPayload` field for field."},"DraftLinkedInRequest":{"properties":{"contact_id":{"type":"integer","title":"Contact Id"},"first_name":{"type":"string","title":"First Name"},"last_name":{"type":"string","title":"Last Name"},"linkedin_action_type":{"type":"string","title":"Linkedin Action Type","description":"The LinkedIn step kind the message is for, e.g. a connection request or a message."},"instructions":{"type":"string","title":"Instructions"},"lead_info":{"type":"string","title":"Lead Info"},"agent_name":{"type":"string","title":"Agent Name","default":"default-agent"},"step_history":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Step History","description":"What earlier steps already said, so the draft does not repeat it."},"studio_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Studio Campaign Id"}},"type":"object","required":["contact_id","first_name","last_name","linkedin_action_type","instructions","lead_info"],"title":"DraftLinkedInRequest","description":"Draft one contact's LinkedIn message. Mirrors `OnDemandLinkedInPayload`."},"DraftResponse":{"properties":{"content":{"type":"string","title":"Content","description":"Generated draft text (HTML)"},"plain_content":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Plain Content","description":"Plain text version"},"credits_charged":{"type":"integer","title":"Credits Charged","default":0}},"type":"object","required":["content"],"title":"DraftResponse"},"DrilldownColumn":{"properties":{"slug":{"type":"string","title":"Slug"},"label":{"type":"string","title":"Label"},"value_type":{"type":"string","title":"Value Type"}},"type":"object","required":["slug","label","value_type"],"title":"DrilldownColumn"},"DrilldownRecord":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"display":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display"},"values":{"additionalProperties":true,"type":"object","title":"Values"},"extra":{"additionalProperties":true,"type":"object","title":"Extra"}},"type":"object","required":["id"],"title":"DrilldownRecord"},"DrilldownRequest":{"properties":{"target":{"oneOf":[{"$ref":"#/components/schemas/GroupTarget"},{"$ref":"#/components/schemas/StageTarget"},{"$ref":"#/components/schemas/SnapshotTarget"},{"$ref":"#/components/schemas/AllTarget"}],"title":"Target","discriminator":{"propertyName":"kind","mapping":{"all":"#/components/schemas/AllTarget","group":"#/components/schemas/GroupTarget","snapshot":"#/components/schemas/SnapshotTarget","stage":"#/components/schemas/StageTarget"}}},"limit":{"type":"integer","maximum":200.0,"minimum":1.0,"title":"Limit","default":50},"after_record_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"After Record Id"}},"additionalProperties":false,"type":"object","required":["target"],"title":"DrilldownRequest","description":"Open the records behind one number: ``target`` is a result row's ``drilldown``, echoed back unchanged."},"DrilldownResult":{"properties":{"kind":{"type":"string","const":"drilldown","title":"Kind","default":"drilldown"},"status":{"type":"string","enum":["ok","restricted"],"title":"Status","default":"ok"},"total":{"type":"integer","title":"Total","default":0},"records":{"items":{"$ref":"#/components/schemas/DrilldownRecord"},"type":"array","title":"Records"},"columns":{"items":{"$ref":"#/components/schemas/DrilldownColumn"},"type":"array","title":"Columns"},"measures":{"additionalProperties":{"anyOf":[{"type":"number"},{"type":"integer"},{"type":"null"}]},"type":"object","title":"Measures"},"next_after_record_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Next After Record Id"},"restricted":{"items":{"$ref":"#/components/schemas/RestrictedComponent"},"type":"array","title":"Restricted"}},"type":"object","title":"DrilldownResult"},"DriverLeaseRequest":{"properties":{"client_id":{"type":"string","maxLength":64,"minLength":1,"pattern":"^[A-Za-z0-9_-]+$","title":"Client Id","description":"Stable id of THIS client (a browser tab, the desktop app, your own app)."},"surface":{"type":"string","enum":["desktop","web"],"title":"Surface","description":"Which kind of client holds the lease."},"session_id":{"anyOf":[{"type":"string","maxLength":128,"pattern":"^[A-Za-z0-9_-]+$"},{"type":"null"}],"title":"Session Id","description":"The dialer session this client is driving, echoed back to other clients as the holder."},"takeover":{"type":"boolean","title":"Takeover","description":"Take the lease from the current holder instead of being refused.","default":false}},"type":"object","required":["client_id","surface"],"title":"DriverLeaseRequest","description":"Take, refresh or take over the per-user dialer driver lease (\"one driver per user\")."},"DuplicateTemplateRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Name"}},"type":"object","title":"DuplicateTemplateRequest","description":"Duplicate a Brand Kit template as another template. Spends nothing."},"EditElementRequest":{"properties":{"selector":{"type":"string","title":"Selector"},"instruction":{"type":"string","title":"Instruction"}},"type":"object","required":["selector","instruction"],"title":"EditElementRequest","description":"Edit one element by CSS selector. SPENDS CREDIT - it is an LLM pass."},"EditImageElementRequest":{"properties":{"index":{"type":"integer","minimum":0.0,"title":"Index"},"text":{"anyOf":[{"type":"string","maxLength":300,"minLength":1},{"type":"null"}],"title":"Text"},"fill":{"anyOf":[{"type":"string","pattern":"^#(?:[0-9a-fA-F]{3}|[0-9a-fA-F]{4}|[0-9a-fA-F]{6}|[0-9a-fA-F]{8})$"},{"type":"null"}],"title":"Fill"},"font_size":{"anyOf":[{"type":"integer","maximum":120.0,"minimum":8.0},{"type":"null"}],"title":"Font Size"}},"type":"object","required":["index"],"title":"EditImageElementRequest","description":"Deterministic in-image edit. NO MODEL RUNS, nothing is spent.\n\nAt least one of `text` / `fill` / `font_size` must be present; `index`\nidentifies which element, from `GET /ad-creatives/{id}/image-elements`."},"EditWithChatRequest":{"properties":{"instruction":{"type":"string","title":"Instruction"},"section_idx":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Section Idx"},"selected_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Selected Text"}},"type":"object","required":["instruction"],"title":"EditWithChatRequest","description":"A natural-language edit instruction. SPENDS CREDIT - it is an LLM pass."},"EmailComposeRequest":{"properties":{"to":{"items":{"type":"string"},"type":"array","minItems":1,"title":"To","description":"Recipients. These are real addresses."},"from_mailbox":{"type":"string","title":"From Mailbox","description":"The mailbox to send AS. Must already be syncing - check with `POST /inbox/emails/validate-mailbox` first."},"content":{"type":"string","title":"Content","description":"Body, HTML."},"subject":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subject","description":"Auto-filled as `Re: {original}` on a reply if omitted."},"cc":{"items":{"type":"string"},"type":"array","title":"Cc"},"bcc":{"items":{"type":"string"},"type":"array","title":"Bcc"},"attachments":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Attachments","description":"Already-uploaded attachment references. The server re-validates each one."},"save_as_draft":{"type":"boolean","title":"Save As Draft","description":"FALSE SENDS THE MESSAGE. True stores a draft and contacts nobody.","default":false},"reply_to_email_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reply To Email Id","description":"Thread to reply into. Omit to start a new conversation."},"draft_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Draft Id","description":"Edit or send an existing draft."},"include_signature":{"type":"boolean","title":"Include Signature","default":true},"assigned_users":{"items":{"type":"string"},"type":"array","title":"Assigned Users","description":"Emails to assign the resulting thread to."},"tag_ids":{"items":{"type":"string"},"type":"array","title":"Tag Ids","description":"Tags to attach to the thread."}},"type":"object","required":["to","from_mailbox","content"],"title":"EmailComposeRequest","description":"Compose an email: save it as a draft, or SEND IT TO A REAL PERSON.\n\n`save_as_draft` decides which. It defaults to FALSE, which means SEND -\nthe app's default, kept rather than made safer here so the two ends cannot\ndisagree about what an omitted field does."},"EmailSearchRequest":{"properties":{"mailboxes":{"items":{"type":"string"},"type":"array","minItems":1,"title":"Mailboxes","description":"Mailbox addresses to search. REQUIRED: the inbox is per-mailbox, and an empty list is not 'all mailboxes', it is no result."},"campaign_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Campaign Ids"},"tag_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Tag Ids"},"exclude_tag_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Exclude Tag Ids"},"search":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Search"},"search_emails":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Search Emails","description":"Return threads touching ANY of these addresses, in the thread owner or in a message's from/to. OR-matched - a scope filter, not a full-text search."},"status":{"anyOf":[{"type":"string","enum":["SENT","AI_RESPONDED","DRAFT"]},{"type":"null"}],"title":"Status","description":"Keep threads in one delivery state. Closed to the three the internal `EmailStatus` enum accepts - an open string here reaches a strict enum inside the handler and raises a bare `pydantic.ValidationError`, which no handler catches, so it escapes as a 500 instead of a 422."},"updated_after":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated After"},"updated_before":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated Before"},"sort_order":{"type":"string","enum":["asc","desc"],"title":"Sort Order","default":"desc"},"sort_by":{"type":"string","enum":["updated_at","created_at","last_message_at"],"title":"Sort By","default":"updated_at"},"assigned_to_user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Assigned To User Email","description":"Only threads assigned to this user."}},"type":"object","required":["mailboxes"],"title":"EmailSearchRequest","description":"Filter and page email threads across one or more mailboxes."},"EmailSendRequest":{"properties":{"content":{"type":"string","title":"Content","description":"Body."},"subject":{"type":"string","title":"Subject","description":"Subject."},"from_email":{"items":{"type":"string"},"type":"array","minItems":1,"title":"From Email"},"to":{"items":{"type":"string"},"type":"array","minItems":1,"title":"To","description":"Recipients. At least one."},"cc_email":{"items":{"type":"string"},"type":"array","title":"Cc Email"},"bcc_email":{"items":{"type":"string"},"type":"array","title":"Bcc Email"},"message_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Message Id","description":"Message being replied to, to keep the thread."}},"type":"object","required":["content","subject","from_email","to"],"title":"EmailSendRequest","description":"The message to send. THIS REACHES A REAL RECIPIENT."},"EmailSettingsRequest":{"properties":{"refresh_rate":{"type":"integer","title":"Refresh Rate","description":"Minutes between sync rounds.","default":1},"timezone":{"type":"string","title":"Timezone","description":"IANA timezone name, e.g. `America/New_York`. Required."},"event_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Event Id","description":"Booking event the AI offers when it schedules a meeting."},"agent_id":{"anyOf":[{"type":"string"},{"type":"integer"},{"type":"null"}],"title":"Agent Id","description":"AI Inbox agent that answers. See `POST /inbox/agents`."},"auto_tagging":{"type":"boolean","title":"Auto Tagging","default":false},"business_hours_only":{"type":"boolean","title":"Business Hours Only","description":"Restrict AI replies to the hours below.","default":false},"business_hours_start":{"type":"integer","title":"Business Hours Start","default":9},"business_hours_end":{"type":"integer","title":"Business Hours End","default":17}},"type":"object","required":["timezone"],"title":"EmailSettingsRequest","description":"Organisation-wide AI Inbox email settings. There is no per-user copy.\n\nThis is a REPLACE, not a merge: the app writes every field, so a value you\nomit is written as its default rather than left alone. Read the current\nsettings first and send them back with your change applied."},"EmailThreadMessage":{"properties":{"subject":{"type":"string","title":"Subject"},"body":{"type":"string","title":"Body"},"sender":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sender"},"timestamp":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Timestamp"}},"type":"object","required":["subject","body"],"title":"EmailThreadMessage","description":"voice `EmailThread`: one earlier message in the thread being answered."},"EmailVerificationConfig":{"properties":{"enabled":{"type":"boolean","title":"Enabled","default":true},"provider":{"type":"string","enum":["zerobounce","hunter","icypeas","leadmagic","emaillistverify"],"title":"Provider","default":"zerobounce"},"use_system_credentials":{"type":"boolean","title":"Use System Credentials","description":"Use graph8's provider keys (charges credits) rather than your own.","default":true},"accept_catchall":{"type":"boolean","title":"Accept Catchall","default":false},"valid_statuses":{"items":{"type":"string"},"type":"array","title":"Valid Statuses"}},"type":"object","title":"EmailVerificationConfig","description":"Verify found emails after the waterfall. PAID per address when\n`use_system_credentials` is true."},"EmailVerificationInput":{"properties":{"enabled":{"type":"boolean","title":"Enabled","description":"Enable post-enrichment email verification","default":true},"provider":{"type":"string","enum":["zerobounce","hunter","icypeas","leadmagic"],"title":"Provider","description":"Verification provider. Charges credits when use_system_credentials=True.","default":"zerobounce"},"use_system_credentials":{"type":"boolean","title":"Use System Credentials","description":"Use graph8-managed API keys (charges credits). False = use org's BYOK keys.","default":true},"accept_catchall":{"type":"boolean","title":"Accept Catchall","description":"Treat catch-all responses as valid (domains that accept any address).","default":false},"valid_statuses":{"items":{"type":"string"},"type":"array","title":"Valid Statuses","description":"Verification statuses to accept as valid. Typical: ['valid'] or ['valid','catch-all']."}},"type":"object","title":"EmailVerificationInput","description":"Email verification config attached to a waterfall pipeline.\n\nMirrors the canonical `EmailVerificationConfigDto` in\n`enrichment/interfaces/fastapi/waterfall_dtos.py` so the dev-API and the\nUI persist an identical settings shape (the CF worker reads `settings.\nemail_verification.*` regardless of which surface saved the pipeline)."},"EmployeeCommissionOverride":{"properties":{"per_meeting_rate":{"type":"number","minimum":0.0,"title":"Per Meeting Rate","default":0.0}},"type":"object","title":"EmployeeCommissionOverride","description":"Optional per-rep commission rate override (else the org default applies)."},"EmployeeCost":{"properties":{"name":{"type":"string","title":"Name","default":""},"role":{"type":"string","enum":["sdr","ae","other"],"title":"Role","default":"other"},"monthly_cost":{"type":"number","minimum":0.0,"title":"Monthly Cost","default":0.0}},"type":"object","title":"EmployeeCost","description":"A single rep's labor cost. ``role`` is informational (sdr/ae/other).\n\n``name`` is intentionally optional (default \"\") at the API layer — direct\nAPI callers may store cost keyed by email alone. The settings UI requires a\nname for usability; a27/a28 fall back to the email for display when blank."},"EnablementAssetUploadRequest":{"properties":{"file_name":{"type":"string","maxLength":255,"minLength":1,"title":"File Name"},"content_base64":{"type":"string","minLength":1,"title":"Content Base64"},"mime_type":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Mime Type"},"folder":{"anyOf":[{"type":"string","maxLength":50},{"type":"null"}],"title":"Folder"},"tags":{"items":{"type":"string"},"type":"array","maxItems":20,"title":"Tags"}},"type":"object","required":["file_name","content_base64"],"title":"EnablementAssetUploadRequest","description":"Base64 file upload for the org's Studio Enablement library."},"EnrichJobResponse":{"properties":{"job_id":{"type":"string","title":"Job Id"},"status":{"type":"string","title":"Status"},"total":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Total"},"completed":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Completed"},"results":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Results"},"successful_enrichments":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Successful Enrichments"},"failed_enrichments":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Failed Enrichments"},"total_credits_used":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Total Credits Used"},"warnings":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Warnings"},"provider_errors":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Provider Errors"}},"type":"object","required":["job_id","status"],"title":"EnrichJobResponse"},"EnrichRequest":{"properties":{"contact_ids":{"items":{"type":"integer"},"type":"array","title":"Contact Ids","description":"Contact IDs to enrich"},"list_id":{"type":"integer","title":"List Id","description":"List ID the contacts belong to"},"fields_config":{"anyOf":[{"additionalProperties":{"items":{"type":"string"},"type":"array"},"type":"object"},{"type":"null"}],"title":"Fields Config","description":"Fields to enrich and provider order. Example: {\"work_email\": [\"prospeo\", \"dropcontact\"]}"}},"type":"object","required":["contact_ids","list_id"],"title":"EnrichRequest","description":"Request to start an async waterfall enrichment job."},"EnrichSeoBulkRequest":{"properties":{"page_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Page Ids"},"limit":{"type":"integer","title":"Limit","description":"Maximum pages enriched, and therefore the maximum spend.","default":50}},"type":"object","title":"EnrichSeoBulkRequest","description":"Bulk SEO enrichment. SPENDS PROVIDER CREDIT, once per page.\n\nOmit `page_ids` to take the next `limit` un-enriched pages. `limit` is the\nceiling on the spend, so send it deliberately rather than by default."},"EnrichmentConfigUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"is_active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Active"}},"additionalProperties":true,"type":"object","title":"EnrichmentConfigUpdateRequest","description":"Fields to change on an enrichment configuration.\n\nA free-form update, matching the app: whatever keys are sent are written.\n`updated_by` is set from the calling key and cannot be supplied."},"EnrichmentListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items","description":"The collection, always present."}},"additionalProperties":true,"type":"object","title":"EnrichmentListPayload","description":"A collection result.\n\n`items` is ALWAYS present, so a caller can iterate without knowing whether\nthe handler returned a bare list or a named key. When the handler used a\nnamed key that key is preserved beside `items` rather than renamed, because\nrenaming it would make the API and the app disagree about the same data."},"EnrichmentPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"EnrichmentPayload","description":"One enrichment object, open-shaped.\n\nOpen on purpose: a workbench column set is defined by the CUSTOMER at\nruntime, and the enrichment result shapes grow with every provider added.\nPinning them would drop whatever a provider returned that this contract had\nnot caught up on, which on an enrichment surface is the data the customer\npaid for."},"EnrichmentPreflightRequest":{"properties":{"list_id":{"type":"integer","title":"List Id","description":"List ID the contacts belong to"},"contact_ids":{"items":{"type":"integer"},"type":"array","title":"Contact Ids","description":"Contact IDs to enrich (duplicates are counted once)"},"mode":{"type":"string","title":"Mode","description":"'auto' (AI when ai_group_id is set, else waterfall), 'waterfall' or 'ai-research'","default":"auto"},"ai_group_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Ai Group Id","description":"group_id of a saved AI enrichment config (required for 'ai-research')"},"providers":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Providers","description":"Ordered provider names for a waterfall run. Omit to use the list's saved pipeline; an empty list also uses the saved pipeline (a warning says so)."},"target_field":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Field","description":"Column to enrich: a canonical CONTACT_*/COMPANY_* column or a synonym like 'phone' or 'email'"},"email_verification":{"type":"boolean","title":"Email Verification","description":"Add ZeroBounce email verification","default":false}},"type":"object","required":["list_id","contact_ids"],"title":"EnrichmentPreflightRequest","description":"Check an enrichment request before running it. Free: nothing is written,\nqueued or charged.\n\nTakes the same inputs as the MCP `g8_enrich_contacts` tool so a preview can\nsay up front whether the run would work."},"EnrichmentPreflightResponse":{"properties":{"list_id":{"type":"integer","title":"List Id"},"list_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"List Name"},"mode":{"type":"string","title":"Mode","description":"Resolved mode: 'waterfall' or 'ai-research'"},"contact_ids":{"items":{"type":"integer"},"type":"array","title":"Contact Ids","description":"Contact IDs that will be enriched: duplicates removed, order kept"},"contact_count":{"type":"integer","title":"Contact Count","description":"Number of unique contacts (the count credits are estimated on)"},"duplicates_removed":{"type":"integer","title":"Duplicates Removed","description":"How many repeated contact IDs were dropped","default":0},"not_in_list":{"items":{"type":"integer"},"type":"array","title":"Not In List","description":"Contact IDs that are not on the list; the run skips them and does not charge for them"},"target_field":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Field","description":"Canonical column for target_field, when given"},"providers":{"items":{"type":"string"},"type":"array","title":"Providers","description":"Providers that would run, in order (empty = the saved pipeline)"},"uses_saved_pipeline":{"type":"boolean","title":"Uses Saved Pipeline","description":"True when the list's saved pipeline (or the graph8 default) would run","default":false},"providers_detail":{"items":{"$ref":"#/components/schemas/ProviderStepDetail"},"type":"array","title":"Providers Detail"},"missing_credentials":{"items":{"type":"string"},"type":"array","title":"Missing Credentials","description":"Providers whose step would be skipped because the org has no key for them"},"warnings":{"items":{"type":"string"},"type":"array","title":"Warnings","description":"Plain-language advisories for the user"},"pipeline_column_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Pipeline Column Id","description":"column_id of the saved waterfall pipeline the run would reuse. Null when the run would create a new pipeline (it is created on confirm) or in 'ai-research' mode. Pass it to POST /enrichment/waterfall/validate-credits for the record-exact quote."},"credits_per_record":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Credits Per Record","description":"Waterfall only: the most one contact can cost, in graph8 credits. A record is charged its dearest graph8-funded step that finds a value (steps are not added together); steps on your own key cost 0. Null when the pipeline could not be priced."},"priced_records":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Priced Records","description":"Waterfall only: contacts the price covers (unique contacts that are on the list)."},"max_total_credits":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Max Total Credits","description":"Waterfall only: priced_records x credits_per_record, the most this run can charge. Records the pipeline skips (values already present, run conditions) cost less. Null when not priced."}},"type":"object","required":["list_id","mode","contact_ids","contact_count"],"title":"EnrichmentPreflightResponse","description":"What a run with these inputs would do. Errors (unknown list, mode, field or\nprovider, impossible contact IDs) come back as 400/404 instead."},"EntityType":{"type":"string","enum":["custom_objects","contacts","companies","deals","leads","lists","contacts_view","companies_view","list_contacts","list_companies","search_people","search_companies","abm_companies","enrichment_workbench","enrichment_workbenches"],"title":"EntityType","description":"Which CRM grid the saved view applies to. Free-form string at the DB\nlevel (cb_saved_views.entity_type is VARCHAR(50)) to avoid a schema\nmigration when we add deals/tasks/leads — but enforced as an enum at the\nAPI boundary so we don't accept typos.\n\nNEITHER A SUBSET NOR A SUPERSET OF ``FilterEntityType`` — see the invariant\non that class, and the sibling docstring below, which states the same\nrelationship from the other side. The two enums overlap on the four GRID\nvalues (``contacts``, ``companies``, ``deals``, ``leads``);\n``FilterEntityType`` is a superset of THOSE and adds ``report``, while the\nnine list/view/search/workbench members here have no counterpart there.\nCustom objects additionally use an object-bound view context.\n\n(This paragraph previously read \"DELIBERATELY NARROWER THAN\n``FilterEntityType``\", which inverted the relationship: this is the LARGER\nenum. The narrowness that matters is real but specific — ``report`` is\nexcluded, and only ``report`` — so stating it as a general containment\ninvited exactly the wrong conclusion about the other nine.)\n\nNative grid members can be saved with ``context_key = NULL`` for reuse\nacross that entity type. CUSTOM_OBJECTS is the exception: it requires an\nimmutable object context and the object-authorized endpoints. It must never\nenter the native grids' reusable saved-filter menus."},"EntryPointCaptureRequest":{"properties":{"entry_point":{"type":"string","enum":["dialer","sequencer","marketplace","dev","calendar","email_inbox","full"],"title":"Entry Point","description":"The signup entry point. Maps 1:1 to a plan template, so this chooses what the agent will propose doing first. FIRST WRITER WINS: if the org already has one captured, this call reports the existing value and changes nothing."}},"type":"object","required":["entry_point"],"title":"EntryPointCaptureRequest","description":"Mirror of `CaptureEntryPointRequest`."},"EnvelopeDocument":{"properties":{"title":{"type":"string","minLength":1,"title":"Title"},"content_html":{"type":"string","minLength":1,"title":"Content Html","description":"The document body as HTML. Rendered to the PDF the signer sees."}},"type":"object","required":["title","content_html"],"title":"EnvelopeDocument","description":"One document inside an envelope.\n\n`content_html` IS the document - there is no upload step and no file. That\nis why this surface has no multipart endpoint: an envelope is created from\nHTML the caller already holds, which is what makes it scriptable."},"EnvelopeListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"},"total":{"type":"integer","title":"Total","default":0},"page":{"type":"integer","title":"Page","default":1},"limit":{"type":"integer","title":"Limit","default":50}},"additionalProperties":true,"type":"object","title":"EnvelopeListPayload","description":"A page of envelopes."},"EnvelopePayload":{"properties":{},"additionalProperties":true,"type":"object","title":"EnvelopePayload","description":"An open envelope for the envelope detail.\n\nOpen on purpose: the detail carries its documents and its whole audit\ntrail, and the audit trail gains event kinds as the product does. Closing\nit would silently drop an event a caller was relying on to know what\nhappened.\n\nNothing secret rides in here: the signer and viewer tokens are the SIGNING\nLINK's credentials and the app's detail projection does not include them."},"EstimateAllRequest":{"properties":{"list_id":{"type":"integer","title":"List Id"}},"type":"object","required":["list_id"],"title":"EstimateAllRequest","description":"Price every visible qualification template against one list. Charges nothing."},"EstimateTestRequest":{"properties":{"mailbox_ids":{"items":{"type":"integer"},"type":"array","title":"Mailbox Ids","description":"The mailboxes the test would send from."}},"type":"object","required":["mailbox_ids"],"title":"EstimateTestRequest","description":"What a placement test WOULD cost. Charges nothing.\n\nWorth calling first: creating the test charges 20 credits per mailbox, and\nthis is the only way to learn the number before spending it."},"EventTypeListItem":{"properties":{"id":{"type":"integer","title":"Id","description":"Event-type integer ID; pass back to launch / PATCH endpoints as `appointment_id`."},"title":{"type":"string","title":"Title","description":"Display title shown on the booking page."},"slug":{"type":"string","title":"Slug","description":"URL-safe slug (the path segment used in `appointments/team/...` links)."},"length":{"type":"integer","title":"Length","description":"Slot duration in minutes."},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"scheduling_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Scheduling Type","description":"Cal.com scheduling type: managed | round_robin | collective | None (= single-host)."},"hidden":{"type":"boolean","title":"Hidden","description":"When True the event type is not bookable publicly. Excluded by default.","default":false},"schedule_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Schedule Id","description":"ID of the availability schedule attached to this event type, if any."}},"type":"object","required":["id","title","slug","length"],"title":"EventTypeListItem","description":"One row in the booking-link picker. `id` feeds `appointment_id` on the launch body."},"EventTypesListResponse":{"properties":{"data":{"items":{"$ref":"#/components/schemas/EventTypeListItem"},"type":"array","title":"Data"}},"type":"object","required":["data"],"title":"EventTypesListResponse","description":"Envelope for `GET /event-types`."},"ExactReplacementRequest":{"properties":{"old":{"type":"string","maxLength":200000,"minLength":1,"title":"Old"},"new":{"type":"string","maxLength":500000,"title":"New"},"expected_matches":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Expected Matches","default":1}},"type":"object","required":["old","new"],"title":"ExactReplacementRequest","description":"One exact replacement applied against the evolving HTML document."},"ExecutionApproval":{"properties":{"workflow_id":{"type":"string","minLength":1,"title":"Workflow Id","description":"The paused run's workflow id."},"approved_by":{"type":"string","minLength":1,"title":"Approved By","description":"Who approved; voice checks they may."},"notes":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Notes"}},"type":"object","required":["workflow_id","approved_by"],"title":"ExecutionApproval","description":"voice `ApprovalRequest`, without `org_id`."},"ExecutionRejection":{"properties":{"workflow_id":{"type":"string","minLength":1,"title":"Workflow Id","description":"The paused run's workflow id."},"rejected_by":{"type":"string","minLength":1,"title":"Rejected By","description":"Who rejected; voice checks they may."},"reason":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Reason"}},"type":"object","required":["workflow_id","rejected_by"],"title":"ExecutionRejection","description":"voice `RejectionRequest`, without `org_id`."},"ExpandArrayRequest":{"properties":{"source_column_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Source Column Id"},"array_field_path":{"type":"string","minLength":1,"title":"Array Field Path"},"keep_parent_fields":{"type":"boolean","title":"Keep Parent Fields","description":"Copy the parent row's other fields onto each new row.","default":true}},"type":"object","required":["array_field_path"],"title":"ExpandArrayRequest","description":"Fan an array field out into one row per element."},"ExpectedStepRequest":{"properties":{"expected_step_order":{"type":"integer","minimum":1.0,"title":"Expected Step Order","description":"The step order the contact is currently on, as last read."}},"type":"object","required":["expected_step_order"],"title":"ExpectedStepRequest","description":"The step the caller last saw. A mismatch is a 409 `step_changed` (the stale-view guard)."},"ExportRequestDto":{"properties":{"date":{"$ref":"#/components/schemas/DateRangeDto"},"rep":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"pipeline":{"anyOf":[{"$ref":"#/components/schemas/UuidFilterGroupDto"},{"type":"null"}]},"stage":{"anyOf":[{"$ref":"#/components/schemas/UuidFilterGroupDto"},{"type":"null"}]},"lifecycle":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"audiences":{"anyOf":[{"$ref":"#/components/schemas/IntIdFilterGroupDto"},{"type":"null"}]},"rec_type":{"anyOf":[{"$ref":"#/components/schemas/IntIdFilterGroupDto"},{"type":"null"}]},"signals_email":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_voice":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_linkedin":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_sms":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_forms":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_website":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_calendar":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_chat":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_intent":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_crm":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_sequence":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_enrichment":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"channel":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"campaign":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"country":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"industry":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"headcount":{"anyOf":[{"$ref":"#/components/schemas/HeadcountFilterGroupDto"},{"type":"null"}]},"grading_bucket":{"anyOf":[{"$ref":"#/components/schemas/GradingBucketFilterGroupDto"},{"type":"null"}]},"objections":{"anyOf":[{"$ref":"#/components/schemas/ObjectionCodeFilterGroupDto"},{"type":"null"}]},"tier":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"pipeline_target":{"anyOf":[{"type":"string","enum":["prospects_meeting","prospects_revenue","customers_revenue"]},{"type":"null"}],"title":"Pipeline Target","default":"prospects_revenue"},"granularity":{"anyOf":[{"type":"string","enum":["day","week","month"]},{"type":"null"}],"title":"Granularity"},"section":{"anyOf":[{"type":"string","maxLength":128},{"type":"null"}],"title":"Section"}},"additionalProperties":false,"type":"object","required":["date"],"title":"ExportRequestDto","description":"Export body — the cohort filter plus the section selector.\n\nThe FE sends ``section`` in the JSON body alongside the filter (see\n``sales-report.service.ts``). Absent / unknown values fall back to the\npersons drill-down CSV, so older clients keep working unchanged.\n\nInherits every AC-3 filter cap from ``FilterQueryDto``, including the\ncross-group ``_bound_total_filter_values`` validator — the export streams\nthe SAME cohort the screen shows, so an uncapped ``/export`` would be a\ndownload-shaped bypass of the cap ``/cohort`` applies."},"ExternalDomainAvailabilityRequest":{"properties":{"domain":{"type":"string","title":"Domain","description":"Domain to check, e.g. acme.com"}},"type":"object","required":["domain"],"title":"ExternalDomainAvailabilityRequest","description":"Check whether a domain can be attached as an external sending domain. SPENDS NOTHING."},"ExtractColumnRequest":{"properties":{"column_name":{"type":"string","maxLength":255,"minLength":1,"pattern":"^[a-z][a-z0-9_]*$","title":"Column Name"},"display_name":{"type":"string","maxLength":255,"minLength":1,"title":"Display Name"},"source_column_id":{"type":"integer","title":"Source Column Id"},"field_path":{"type":"string","minLength":1,"title":"Field Path","description":"Dot path inside the raw JSON."},"data_type":{"type":"string","enum":["text","number","boolean","json"],"title":"Data Type","default":"text"}},"type":"object","required":["column_name","display_name","source_column_id","field_path"],"title":"ExtractColumnRequest","description":"Create one column from a JSON path inside a raw column."},"ExtractCompanyDataRequest":{"properties":{"website_url":{"type":"string","minLength":1,"title":"Website Url","description":"Company website to extract from. Intelligence data for it must already exist."},"enrich":{"type":"boolean","title":"Enrich","description":"Enrich the extracted fields through Apollo. SPENDS CREDITS - the call is credit-gated and answers 402 when the balance is short.","default":true}},"type":"object","required":["website_url"],"title":"ExtractCompanyDataRequest","description":"The typed form of the untyped `dict` body `extract-company-data` takes.\n\nThe app reads exactly two keys off that dict and 400s when `website_url` is\nmissing. Typed here so the same mistake is a parse-layer 422 naming the\nfield, and so the caller can see that `enrich` exists at all - it is\ninvisible in an untyped body.\n\nNOT a mirrored model: there is no app model to mirror. The proxy sends a\nplain dict, exactly as the browser does."},"ExtractImagesRequest":{"properties":{"url":{"type":"string","title":"Url"},"min_width":{"type":"integer","title":"Min Width","default":200},"min_height":{"type":"integer","title":"Min Height","default":200}},"type":"object","required":["url"],"title":"ExtractImagesRequest","description":"Pull images out of a website. Fetches the site; spends no credit."},"FailureRuleRequest":{"properties":{"channel":{"type":"string","title":"Channel","description":"Channel the injected failure applies to: email, sms, whatsapp, voice, linkedin, crm, ads, calendar, or '*' for every channel."},"failure_mode":{"type":"string","title":"Failure Mode","description":"One of: hard_bounce, provider_error, timeout, rate_limited, invalid_recipient."},"remaining":{"anyOf":[{"type":"integer","maximum":10000.0,"minimum":1.0},{"type":"null"}],"title":"Remaining","description":"Fail this many sends, then auto-clear. Omit to fail until cleared."}},"type":"object","required":["channel","failure_mode"],"title":"FailureRuleRequest"},"FailureRulesResponse":{"properties":{"sandbox":{"type":"boolean","title":"Sandbox","default":true},"rules":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Rules"}},"type":"object","required":["rules"],"title":"FailureRulesResponse"},"FetchContactsRequest":{"properties":{"filter":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Filter","description":"Serialized per-column filter JSON. Omit for no filter."},"page":{"type":"integer","minimum":1.0,"title":"Page","description":"Page number (1-indexed).","default":1},"limit":{"type":"integer","maximum":1000.0,"minimum":1.0,"title":"Limit","description":"Records per page.","default":50},"mapping_columns":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Mapping Columns","description":"Columns to return. Omit for every column."}},"type":"object","title":"FetchContactsRequest","description":"Page through contacts, optionally projecting a narrow column set.\n\n`mapping_columns` is not only a smaller payload: naming a narrow set lets\nthe planner drop joins the full row would force, so it is materially\ncheaper on a wide org."},"FieldPolicy":{"properties":{"mode":{"type":"string","enum":["preserve","fill_missing","source_owned","replace"],"title":"Mode","default":"fill_missing"},"preserve_manual_edits":{"type":"boolean","title":"Preserve Manual Edits","default":true},"empty_source":{"type":"string","enum":["ignore","explicit_retraction"],"title":"Empty Source","default":"ignore"}},"additionalProperties":false,"type":"object","title":"FieldPolicy","description":"How one field is reconciled when the source and the record disagree."},"FieldResponse":{"properties":{"id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Id"},"title":{"type":"string","title":"Title"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"data_type":{"type":"string","title":"Data Type","default":"text"},"is_global":{"type":"boolean","title":"Is Global","default":true},"label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Label","description":"Human-readable field name for display, e.g. 'First name' for CONTACT_FIRST_NAME. Custom columns use their title. Keep using `name` as the identifier."}},"type":"object","required":["title"],"title":"FieldResponse"},"FieldValueItem":{"properties":{"column_id":{"type":"integer","title":"Column Id","description":"Column ID from g8_list_fields or g8_create_field."},"value":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Value","description":"Value to write into the custom column. Pass null (or omit) to clear the field."}},"type":"object","required":["column_id"],"title":"FieldValueItem","description":"One (column, value) pair to write on a row."},"FillColumnPreviewBody":{"properties":{"provider":{"type":"string","title":"Provider","description":"Provider name (e.g., 'formula', 'ai', 'apollo')"},"e_column_id":{"type":"string","title":"E Column Id","description":"Enrichment column ID (source)"},"column_id":{"type":"string","title":"Column Id","description":"Destination column: UDO (udo_*) or standard (CONTACT_*, COMPANY_*)"},"list_id":{"type":"integer","title":"List Id","description":"List ID to scope the fill operation"}},"type":"object","required":["provider","e_column_id","column_id","list_id"],"title":"FillColumnPreviewBody","description":"What moving an enrichment column's values into a destination column would change, without writing."},"FillColumnPreviewPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"FillColumnPreviewPayload","description":"`column_name`, `column_category`, `record_type`, `target_records` and `non_empty_values`."},"FilterCondition":{"properties":{"field":{"type":"string","title":"Field","description":"Field name to apply the condition to."},"operator":{"type":"string","title":"Operator","description":"Operator, e.g. `=`, `in`, `like`.","default":"="},"value":{"title":"Value","description":"Value to compare against."},"value_to":{"anyOf":[{},{"type":"null"}],"title":"Value To","description":"Secondary value, for range operators."}},"type":"object","required":["field"],"title":"FilterCondition","description":"One structured filter condition.\n\nMirrors `shared.interfaces.fastapi.dtos.DtoCondition`."},"FilterGroupDto":{"properties":{"in":{"items":{"type":"string","maxLength":512},"type":"array","maxItems":1000,"title":"In"},"not":{"type":"boolean","title":"Not","default":false}},"additionalProperties":false,"type":"object","title":"FilterGroupDto","description":"One filter group — list of values + optional NOT toggle.\n\n``in_`` is capped at ``MAX_FILTER_VALUES_PER_GROUP`` items of\n``MAX_FILTER_VALUE_LENGTH`` characters each. Over-cap input raises during\nbody parsing, so FastAPI answers 422 with the offending group named in\n``detail[].loc`` (``[\"body\", \"<group>\", \"in\"]``) and the cap in\n``detail[].msg`` — no handler code, and therefore no SQL, runs.\n\nTHIS SHAPE DOES NOT NEST. ``in_`` holds scalars and there is no\ngroup-of-groups member, so a caller cannot vary the tree depth: it is fixed\nat 2 (query -> group -> values) by construction, and ``extra=\"forbid\"`` on\nboth models keeps it that way. A depth check here would be validation that\ncan never fire. Add one WITH the member that introduces nesting, not before\nit.\n\nDo not confuse this with ``SegmentFilterGroup``\n(``contacts/domain/value_objects/ag_grid_models.py:111``), which IS\nrecursive and is where AC-3's \"tree depth\" belongs. Different model,\ndifferent route, still unbounded — see the scope note above the constants."},"FilterOptionItem":{"properties":{"id":{"type":"string","title":"Id","description":"Normalised value - this is what you send back as a filter value."},"label":{"type":"string","title":"Label","description":"The value as it is spelled in the data, for display."},"count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Count","description":"Records carrying this value, when the backend computed it."},"aliases":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Aliases","description":"Other spellings a person might type (`USA`, `UK`)."}},"additionalProperties":true,"type":"object","required":["id","label"],"title":"FilterOptionItem","description":"One distinct value a field can hold."},"FilterOptionsRequest":{"properties":{"filters":{"items":{"$ref":"#/components/schemas/SearchFilter"},"type":"array","title":"Filters","description":"Filter conditions (AND logic)"},"page":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Page","description":"Page number (1-indexed)","default":1},"limit":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Limit","description":"Results per page (max 100)","default":25},"resource":{"type":"string","enum":["contacts","companies"],"title":"Resource","description":"Which index the field names belong to. Decides the vocabulary."},"fields":{"items":{"type":"string"},"type":"array","minItems":1,"title":"Fields","description":"Developer field names, as used by `POST /search/{resource}`."}},"additionalProperties":false,"type":"object","required":["resource","fields"],"title":"FilterOptionsRequest","description":"Ask what values a set of fields holds, narrowed by a search.\n\nMirrors the app's `FilteredFilterOptionsRequest` in substance - `fields`\nplus an ICP query - but in the PUBLISHED vocabulary.\n\nIt SUBCLASSES the published `SearchRequest` rather than restating its\nfields, so `filters`, `page` and `limit` cannot drift away from the search\nthey are meant to describe: a body that works against\n`POST /search/contacts` works here with two fields added.\n\n`filters` must be non-empty. That is not this contract being fussy - it is\nthe same refusal `POST /search/contacts` makes, because an unfiltered\nrequest scans the entire open-data index."},"FilterPredicate":{"properties":{"field":{"type":"string","title":"Field"},"op":{"type":"string","title":"Op"},"value":{"anyOf":[{},{"type":"null"}],"title":"Value"},"values":{"anyOf":[{"items":{},"type":"array"},{"type":"null"}],"title":"Values"},"conditions":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Conditions","description":"Nested predicates for AND/OR groups. Each entry has the same shape as this object: field, op, value, values and, optionally, its own conditions."}},"type":"object","required":["field","op"],"title":"FilterPredicate","description":"One clause of a queue filter. `conditions` nests for AND/OR groups.\n\n`conditions` is typed as a list of plain objects rather than as a list of\n`FilterPredicate`, ON PURPOSE. Voice's own model IS recursive, and this\none was too, which made it the only self-referencing schema in the\npublished contract - and the developer-docs renderer recurses on a\nself-referencing schema with no depth limit until Node runs out of memory\n(`verify-help-docs` and `User help coverage and rendering` both died with\nexit 134 on every head that carried it). The wire format is unchanged:\neach entry has this same shape (`field`, `op`, `value`, `values`,\n`conditions`) and is forwarded to voice as-is, which validates it against\nits recursive model. The parity test compares field NAMES, so it still\npins this model to voice's."},"FilterQueryDto":{"properties":{"date":{"$ref":"#/components/schemas/DateRangeDto"},"rep":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"pipeline":{"anyOf":[{"$ref":"#/components/schemas/UuidFilterGroupDto"},{"type":"null"}]},"stage":{"anyOf":[{"$ref":"#/components/schemas/UuidFilterGroupDto"},{"type":"null"}]},"lifecycle":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"audiences":{"anyOf":[{"$ref":"#/components/schemas/IntIdFilterGroupDto"},{"type":"null"}]},"rec_type":{"anyOf":[{"$ref":"#/components/schemas/IntIdFilterGroupDto"},{"type":"null"}]},"signals_email":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_voice":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_linkedin":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_sms":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_forms":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_website":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_calendar":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_chat":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_intent":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_crm":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_sequence":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"signals_enrichment":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"channel":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"campaign":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"country":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"industry":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"headcount":{"anyOf":[{"$ref":"#/components/schemas/HeadcountFilterGroupDto"},{"type":"null"}]},"grading_bucket":{"anyOf":[{"$ref":"#/components/schemas/GradingBucketFilterGroupDto"},{"type":"null"}]},"objections":{"anyOf":[{"$ref":"#/components/schemas/ObjectionCodeFilterGroupDto"},{"type":"null"}]},"tier":{"anyOf":[{"$ref":"#/components/schemas/FilterGroupDto"},{"type":"null"}]},"pipeline_target":{"anyOf":[{"type":"string","enum":["prospects_meeting","prospects_revenue","customers_revenue"]},{"type":"null"}],"title":"Pipeline Target","default":"prospects_revenue"},"granularity":{"anyOf":[{"type":"string","enum":["day","week","month"]},{"type":"null"}],"title":"Granularity"}},"additionalProperties":false,"type":"object","required":["date"],"title":"FilterQueryDto","description":"JSON shape consumed by POST /api/sales-report/cohort.\n\nEmpty groups are omitted by callers; absent groups treated as empty."},"FilterSpec":{"properties":{"search":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Search"},"predicates":{"items":{"$ref":"#/components/schemas/FilterPredicate"},"type":"array","title":"Predicates"},"exclude_dispositions":{"items":{"type":"string"},"type":"array","title":"Exclude Dispositions"}},"type":"object","title":"FilterSpec","description":"Which contacts in the list are eligible to be dialed.\n\nNarrowing this on a RUNNING session changes who gets called next. It is\nnot a display filter."},"FilterSpecPatchRequest":{"properties":{"filter_spec":{"anyOf":[{"$ref":"#/components/schemas/FilterSpec"},{"type":"null"}]},"order_spec":{"anyOf":[{"$ref":"#/components/schemas/OrderSpec"},{"type":"null"}]}},"type":"object","title":"FilterSpecPatchRequest","description":"Mirrors `FilterSpecPatchRequest`. Changes WHO GETS CALLED NEXT."},"FindPeopleSearchFilter":{"properties":{"field":{"type":"string","maxLength":255,"minLength":1,"title":"Field"},"operator":{"type":"string","enum":["any_of","any_of_with_simular","any_off","any_off_with_simular","all_of","none_of","empty","not_empty","exists","between","include_lists","exclude_lists","include_topics","include_keywords"],"title":"Operator"},"value":{"items":{"type":"string"},"type":"array","title":"Value"}},"type":"object","required":["field","operator"],"title":"FindPeopleSearchFilter","description":"One condition narrowing the people search."},"FixtureActionResponse":{"properties":{"sandbox":{"type":"boolean","title":"Sandbox","default":true},"action":{"type":"string","title":"Action"},"companies":{"type":"integer","title":"Companies","default":0},"contacts":{"type":"integer","title":"Contacts","default":0},"detail":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Detail"}},"type":"object","required":["action"],"title":"FixtureActionResponse"},"FolderTemplateItem":{"properties":{"key":{"type":"string","title":"Key","description":"Stable key used for mapping (e.g. `transcripts`)."},"name":{"type":"string","title":"Name","description":"Display name in the folder tree."},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Optional helper text."},"locked":{"type":"boolean","title":"Locked","description":"When true the folder cannot be renamed or removed.","default":false}},"type":"object","required":["key","name"],"title":"FolderTemplateItem","description":"Mirrors `campaign_builder.schemas.settings.ClientFolderTemplateItem`."},"FolderTemplateUpdateRequest":{"properties":{"folders":{"items":{"$ref":"#/components/schemas/FolderTemplateItem"},"type":"array","title":"Folders","description":"The complete folder template. Anything omitted is removed."}},"type":"object","title":"FolderTemplateUpdateRequest","description":"Mirrors `UpdateClientFolderTemplateRequest`. REPLACES the template."},"ForceNextContact":{"properties":{"contact_id":{"type":"string","title":"Contact Id"},"phone_field":{"type":"string","title":"Phone Field"}},"type":"object","required":["contact_id","phone_field"],"title":"ForceNextContact","description":"Jump one specific contact to the front of the next batch."},"FormBackfillRequest":{"properties":{"source_id":{"type":"string","maxLength":500,"minLength":1,"title":"Source Id","description":"The site (write key) the form is installed on."},"start_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Start At"},"end_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"End At"},"preview":{"type":"boolean","title":"Preview","description":"True reports what would be delivered without delivering it.","default":true},"estimated":{"type":"integer","minimum":0.0,"title":"Estimated","description":"The count a preview reported, echoed back.","default":0}},"additionalProperties":false,"type":"object","required":["source_id"],"title":"FormBackfillRequest","description":"Re-deliver submissions captured in a window. Mirrors `BackfillRequest`.\n\n`preview` DEFAULTS TO TRUE, as it does in the app: a real backfill delivers\nreal leads to the form's route and cannot be undone."},"FormCaptureSettingsRequest":{"properties":{"allowed_hosts":{"items":{"type":"string"},"type":"array","title":"Allowed Hosts","description":"Capture only on these hosts. Empty means every host."},"blocked_hosts":{"items":{"type":"string"},"type":"array","title":"Blocked Hosts","description":"Never capture on these hosts."},"blocked_paths":{"items":{"type":"string"},"type":"array","title":"Blocked Paths","description":"Never capture on these URL paths."},"track_appointments":{"type":"boolean","title":"Track Appointments","description":"Also capture booking-form submissions.","default":true}},"type":"object","title":"FormCaptureSettingsRequest","description":"Which pages form submissions are captured from.\n\nA FULL REPLACEMENT: every list is written as sent, so an omitted list is\nreset to empty and an omitted `track_appointments` goes back to true. Read\n`GET /visitors/form-capture-settings` first and send the whole object back."},"FormFieldMapping":{"properties":{"source_field":{"type":"string","title":"Source Field","description":"Name of the submitted form field."},"target_field":{"type":"string","title":"Target Field","description":"Contact field it is written to."},"is_new_column":{"type":"boolean","title":"Is New Column","description":"Whether `target_field` is a dynamic column created by this mapping.","default":false},"new_column_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"New Column Name","description":"Display name of that dynamic column."},"dynamic_column_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Dynamic Column Id","description":"Id of that dynamic column."},"static_value":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Static Value","description":"Constant written to `target_field` instead of reading a submitted field."}},"type":"object","required":["source_field","target_field"],"title":"FormFieldMapping","description":"One submitted field and the contact field it lands in. Mirrors `MappedFieldName`."},"FormGroupCreateRequest":{"properties":{"name":{"type":"string","maxLength":200,"minLength":1,"title":"Name"},"form_type":{"anyOf":[{"type":"string","enum":["lead","newsletter","meeting","contact","download","other"]},{"type":"null"}],"title":"Form Type"},"members":{"items":{"$ref":"#/components/schemas/FormGroupMemberRef"},"type":"array","maxItems":200,"title":"Members"}},"additionalProperties":false,"type":"object","required":["name"],"title":"FormGroupCreateRequest","description":"Mirrors `CuratedGroupCreateRequest`. Members already in another group are MOVED here."},"FormGroupMemberRef":{"properties":{"source_id":{"type":"string","maxLength":500,"minLength":1,"title":"Source Id","description":"Write key, or its bare key id."},"form_key":{"type":"string","maxLength":500,"minLength":1,"title":"Form Key"}},"additionalProperties":false,"type":"object","required":["source_id","form_key"],"title":"FormGroupMemberRef","description":"One inventory row in a curated group. Mirrors `GroupMemberRefRequest`."},"FormGroupMembersRequest":{"properties":{"members":{"items":{"$ref":"#/components/schemas/FormGroupMemberRef"},"type":"array","maxItems":200,"minItems":1,"title":"Members"}},"additionalProperties":false,"type":"object","required":["members"],"title":"FormGroupMembersRequest","description":"Mirrors `CuratedGroupMembersRequest`."},"FormGroupPatchRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":200,"minLength":1},{"type":"null"}],"title":"Name"},"form_type":{"anyOf":[{"type":"string","enum":["lead","newsletter","meeting","contact","download","other"]},{"type":"null"}],"title":"Form Type"}},"additionalProperties":false,"type":"object","title":"FormGroupPatchRequest","description":"Mirrors `CuratedGroupPatchRequest`."},"FormGroupSyncRequest":{"properties":{"source_id":{"type":"string","maxLength":500,"title":"Source Id"},"group_id":{"type":"string","maxLength":200,"minLength":1,"title":"Group Id"},"axis":{"type":"string","enum":["fields","component","page","campaign","source_attribute"],"title":"Axis"},"matcher":{"type":"string","maxLength":2000,"title":"Matcher","description":"The axis value this group covers.","default":""},"name":{"type":"string","maxLength":200,"title":"Name","default":""},"target_list_id":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Target List Id"}},"type":"object","required":["source_id","group_id","axis"],"title":"FormGroupSyncRequest","description":"Name one group of id-less submissions and route its leads to a list. Mirrors `GroupSyncRequest`."},"FormGroupingRuleRequest":{"properties":{"source_id":{"type":"string","maxLength":500,"title":"Source Id"},"axis":{"type":"string","enum":["none","fields","component","page","campaign","source_attribute"],"title":"Axis","default":"none"}},"type":"object","required":["source_id"],"title":"FormGroupingRuleRequest","description":"How one site's id-less submissions are split into forms. Mirrors `GroupingRuleRequest`."},"FormInventoryFilters":{"properties":{"page":{"type":"integer","minimum":1.0,"title":"Page","default":1},"per_page":{"type":"integer","maximum":500.0,"minimum":1.0,"title":"Per Page","default":20},"write_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Write Key"},"sort_field":{"anyOf":[{"type":"string","enum":["submissions_30d","total_submissions","latest_submitted_at","form_tag_id"]},{"type":"null"}],"title":"Sort Field"},"sort_order":{"anyOf":[{"type":"string","enum":["asc","desc"]},{"type":"null"}],"title":"Sort Order"},"source_id":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Source Id"},"search":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Search"},"has_new_fields":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Has New Fields"},"destination_list_id":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Destination List Id"},"mapping_state":{"anyOf":[{"type":"string","enum":["mapped","unmapped"]},{"type":"null"}],"title":"Mapping State"},"capture_health":{"anyOf":[{"type":"string","enum":["healthy","no_data"]},{"type":"null"}],"title":"Capture Health"},"delivery_state":{"anyOf":[{"type":"string","enum":["active","paused","failed","not_configured"]},{"type":"null"}],"title":"Delivery State"},"has_failures":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Has Failures"},"owner_id":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Owner Id"},"identity_quality":{"anyOf":[{"type":"string","enum":["verified","variant","collision","historic_uncertain"]},{"type":"null"}],"title":"Identity Quality"},"activity_start":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Activity Start"},"activity_end":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Activity End"},"saved_view":{"anyOf":[{"type":"string","enum":["live","needs_setup","failing","ignored","healthy","failures","new_fields","no_recent_submissions","missing_or_collision","destination_unavailable","newly_discovered"]},{"type":"null"}],"title":"Saved View"}},"additionalProperties":false,"type":"object","title":"FormInventoryFilters","description":"The inventory filter set a saved view stores. Mirrors `PaginationRequest`."},"FormMappingRequest":{"properties":{"source_id":{"anyOf":[{"type":"string","maxLength":500,"minLength":1},{"type":"null"}],"title":"Source Id"},"expected_route_version":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Expected Route Version","description":"Optimistic-concurrency guard: the route version you last read. Omit for last-writer-wins."},"submissions_page":{"type":"integer","minimum":1.0,"title":"Submissions Page","default":1},"submissions_per_page":{"type":"integer","minimum":1.0,"title":"Submissions Per Page","default":20},"form_to_contact_field_mapping":{"items":{"$ref":"#/components/schemas/FormFieldMapping"},"type":"array","title":"Form To Contact Field Mapping","description":"Submitted field -> contact field."},"target_list_name":{"type":"string","title":"Target List Name","description":"Name of the list the mapped submissions are saved to."},"target_list_id":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Target List Id","description":"Id of that list, when it already exists."}},"type":"object","required":["target_list_name"],"title":"FormMappingRequest","description":"How a form's submitted fields become contact fields.\n\nMirrors `PreviewFormToContactMappingRequest`, which the app uses for both\nthe preview and the save."},"FormOverview":{"properties":{"form_key":{"type":"string","title":"Form Key"},"source_id":{"type":"string","title":"Source Id"},"technical_form_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Technical Form Id"},"display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display Name"},"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id"},"identity_state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Identity State"},"placement_count":{"type":"integer","title":"Placement Count","default":0},"capture_health":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Capture Health"},"delivery_health":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Delivery Health"},"activation_health":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Activation Health"},"metrics":{"additionalProperties":true,"type":"object","title":"Metrics"},"last_destination_verified_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Last Destination Verified At"},"recommended_action":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Recommended Action"},"last_processed_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Last Processed At","description":"When a submission of this form was last processed for delivery."},"delivery_source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Delivery Source","description":"Where leads go: 'route' (tracked delivery route), 'legacy_mapping' (older list mapping; delivered, but processed/failed stay 0 because it writes no receipts) or null (nowhere)."},"destination":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Destination","description":"The destination list: {list_id, route_version, source, list_name?}; null when none."},"delivery_warning":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Delivery Warning","description":"Plain-language delivery problem, e.g. captured leads with no destination."},"setup_hints":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Setup Hints","description":"What is missing for someone to own this form's leads: [{code, message}], e.g. owner_missing."}},"type":"object","required":["form_key","source_id"],"title":"FormOverview","description":"Per-form operational detail (health, metrics, destination).\n\nMirrors the scalar fields of the in-app ``GET /forms/{form_key}/overview``\nresponse. The config-oriented ``route`` / ``permissions`` blocks from the\ninternal payload are intentionally omitted — an agent describing a form does\nnot need route-editing internals."},"FormPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"FormPayload","description":"An open envelope for a form operational view.\n\n`overview`, `fields`, `placements`, `activity`, a route save result and a\nsubmission trace each return a different shape assembled from several\nupstreams. Pinning any of them would drop a field the moment one is added,\nand on a delivery-diagnostics surface a missing field reads as a missing\ndelivery."},"FormPlacementPreviewRequest":{"properties":{"source_id":{"type":"string","maxLength":500,"minLength":1,"title":"Source Id","description":"The site (write key) the form is installed on."},"page_url":{"type":"string","maxLength":4096,"minLength":8,"title":"Page Url","description":"A page the form was actually seen on."}},"additionalProperties":false,"type":"object","required":["source_id","page_url"],"title":"FormPlacementPreviewRequest","description":"Which observed placement to capture. Mirrors `PlacementPreviewRequest`."},"FormRegistryPatchRequest":{"properties":{"source_id":{"type":"string","maxLength":500,"minLength":1,"title":"Source Id","description":"Which INSTALLED SOURCE of this form. A form key can be present on more than one source, and every operation on this surface is scoped to one - omitting it would silently act on whichever the backend picked."},"display_name":{"anyOf":[{"type":"string","maxLength":200,"minLength":1},{"type":"null"}],"title":"Display Name"},"owner_id":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Owner Id"},"archived":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Archived","description":"Archive or unarchive. Omit to leave unchanged."}},"additionalProperties":false,"type":"object","required":["source_id"],"title":"FormRegistryPatchRequest","description":"Rename, reassign or archive a form."},"FormRouteRequest":{"properties":{"source_id":{"type":"string","maxLength":500,"minLength":1,"title":"Source Id"},"target_list_id":{"type":"integer","minimum":1.0,"title":"Target List Id","description":"Audience list submissions land in."},"mapping":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Mapping","description":"Form field -> graph8 field."},"defaults":{"additionalProperties":true,"type":"object","title":"Defaults","description":"Values applied to every submission."},"workflow_policy":{"type":"string","enum":["disabled","simulate","enabled"],"title":"Workflow Policy","description":"Whether routed submissions trigger workflows. `simulate` records what WOULD have run without running it - the safe way to turn automation on for a live form. Defaults to `disabled`.","default":"disabled"},"expected_schema_version":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Expected Schema Version","description":"PRECONDITION, not a setting. The form schema version this mapping was built against; the save is rejected if the form has changed shape since. Omitting it saves a mapping against a schema you have not seen."},"schema_drift_approved":{"type":"boolean","title":"Schema Drift Approved","description":"Save anyway when the schema HAS drifted. Deliberate override.","default":false},"expected_current_route_version":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Expected Current Route Version","description":"PRECONDITION. The route version you are replacing. Without it the save is last-writer-wins and can silently overwrite a colleague's route."},"expected_route_history_version":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Expected Route History Version","description":"PRECONDITION on the route's history log."}},"additionalProperties":false,"type":"object","required":["source_id","target_list_id"],"title":"FormRouteRequest","description":"Save a form's route: where its submissions land, and how they map.\n\n`extra=\"forbid\"` mirrors the app. An unknown key here is a typo in a\ncaller's mapping, and silently dropping it would send submissions to the\nright list with the wrong fields."},"FormRouteRollbackRequest":{"properties":{"source_id":{"type":"string","maxLength":500,"minLength":1,"title":"Source Id"},"restore_version":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Restore Version","description":"Version to restore. Omit to take the previous one."},"cancel_current":{"type":"boolean","title":"Cancel Current","description":"Cancel a pending route instead of restoring an old one.","default":false},"expected_current_version":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Expected Current Version","description":"PRECONDITION: the version you believe is live. Guards a concurrent rollback."}},"additionalProperties":false,"type":"object","required":["source_id"],"title":"FormRouteRollbackRequest","description":"Roll a route back to an earlier version, or cancel the pending one.\n\nSent as the body of a DELETE, matching the app: this is not \"delete the\nroute\", it is \"move it back\", and which version to move to has to travel\nwith the request."},"FormSavedViewRequest":{"properties":{"name":{"type":"string","maxLength":100,"minLength":1,"title":"Name"},"filters":{"$ref":"#/components/schemas/FormInventoryFilters"}},"additionalProperties":false,"type":"object","required":["name","filters"],"title":"FormSavedViewRequest","description":"A named inventory filter set. Mirrors `SavedFormsViewRequest`."},"FormSiteAuditStatusRequest":{"properties":{"status":{"type":"string","enum":["open","acknowledged","ignored","resolved"],"title":"Status"}},"additionalProperties":false,"type":"object","required":["status"],"title":"FormSiteAuditStatusRequest","description":"Mirrors `SiteAuditStatusRequest`."},"FormSourceScopedRequest":{"properties":{"source_id":{"type":"string","maxLength":500,"minLength":1,"title":"Source Id"}},"additionalProperties":false,"type":"object","required":["source_id"],"title":"FormSourceScopedRequest","description":"Every form operation is scoped to one installed source."},"FormSubmissionCondition":{"properties":{"field":{"type":"string","title":"Field","description":"Submitted field name, or a submission attribute."},"operator":{"type":"string","title":"Operator","description":"Comparison operator, in the app's filter grammar."},"value":{"title":"Value","description":"Value compared against."},"value_to":{"title":"Value To","description":"Upper bound, for range operators."}},"type":"object","required":["field","operator","value"],"title":"FormSubmissionCondition","description":"One filter over a form's submissions. Mirrors the app's `ConditionRequest`."},"FormSubmissionsSearchRequest":{"properties":{"page":{"type":"integer","minimum":1.0,"title":"Page","default":1},"per_page":{"type":"integer","minimum":1.0,"title":"Per Page","default":20},"conditions":{"items":{"$ref":"#/components/schemas/FormSubmissionCondition"},"type":"array","title":"Conditions"},"source_id":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Source Id","description":"One site. Omit for every site the form is on."}},"type":"object","title":"FormSubmissionsSearchRequest","description":"Which page of a form's submissions to read. Mirrors `FormSubmissionsRequest`."},"FormSummary":{"properties":{"id":{"type":"string","title":"Id","description":"The form's HTML tag id (or the id-less group key)."},"form_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Form Key","description":"Alias for id; the addressable key for detail lookups."},"source_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Id","description":"Write key / site the form was submitted from."},"display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display Name","description":"Human-friendly name for the form."},"latest_submitted_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Latest Submitted At","description":"Most recent submission timestamp."},"total_submissions":{"type":"integer","title":"Total Submissions","description":"Total submissions received for this form.","default":0},"page_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Page Url","description":"URL of a page where the form was submitted."},"target_list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Target List Id","description":"Destination list id, if the form is routed."},"target_list_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target List Name","description":"Destination list name, if the form is routed."},"delivery_source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Delivery Source","description":"Where this form's leads are delivered: 'route' (a tracked delivery route), 'legacy_mapping' (an older list mapping, delivered but not tracked per submission) or 'none' (nowhere). Same value the overview reports."},"delivery_health":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Delivery Health","description":"'failing' when at least one submission failed delivery; null otherwise."},"failed_submissions":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Failed Submissions","description":"Submissions whose delivery failed or was only partly delivered (same count as the overview)."}},"type":"object","required":["id"],"title":"FormSummary","description":"One lead-capture form as returned by the list/search endpoint."},"FormsAdminPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"FormsAdminPayload","description":"One forms object, or one handler response.\n\nOpen-shaped: the submission, mapping, group and audit payloads grow with\nthe product, and a closed model here would silently drop what it does not\nname."},"FormsListResponse":{"properties":{"items":{"items":{"$ref":"#/components/schemas/FormSummary"},"type":"array","title":"Items"},"page":{"type":"integer","title":"Page","default":1},"per_page":{"type":"integer","title":"Per Page","default":20},"total":{"type":"integer","title":"Total","default":0}},"type":"object","title":"FormsListResponse","description":"Paginated envelope for the forms list/search endpoint."},"FormulaConfigDto":{"properties":{"formula":{"type":"string","title":"Formula"},"ai_prompt":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Ai Prompt"},"complexity":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Complexity"},"explanation":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Explanation"},"field_dependencies":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Field Dependencies"},"output_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Output Type"}},"type":"object","required":["formula"],"title":"FormulaConfigDto","description":"A formula and the metadata that explains it."},"FormulaFunctionsPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"FormulaFunctionsPayload","description":"The functions a formula can call: `functions[]` with `name`, `category`, `signature`, `description`, `example`."},"FormulaInput":{"properties":{"expression":{"additionalProperties":true,"type":"object","title":"Expression"}},"type":"object","required":["expression"],"title":"FormulaInput","description":"Guided-builder input for a computed field (CRM-06): only the typed JSON expression. The result type,\ncurrency, dependencies, input closure and rollup flag are computed and stored server side at save time --\nnever accepted from a client. A rollup is a ``rollup`` node (the whole expression, or nested)."},"FormulaOutputColumnDef":{"properties":{"name":{"type":"string","maxLength":255,"minLength":1,"pattern":"^[a-z][a-z0-9_]*$","title":"Name"},"display_name":{"type":"string","maxLength":255,"minLength":1,"title":"Display Name"}},"type":"object","required":["name","display_name"],"title":"FormulaOutputColumnDef","description":"One output of a multi-output formula."},"FormulaValidateRequest":{"properties":{"expression":{"additionalProperties":true,"type":"object","title":"Expression","description":"The typed JSON expression (a node tree; a rollup is a `rollup` node)."},"attribute_slug":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Attribute Slug","description":"Slug of the computed field being EDITED (checked against its own place in the dependency graph); omit for a new one."},"preview_record_id":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Preview Record Id","description":"Evaluate the expression against this record's current values."}},"additionalProperties":false,"type":"object","required":["expression"],"title":"FormulaValidateRequest","description":"Dry-run check of a typed formula expression. Nothing is persisted or locked."},"FormulaValidateResponse":{"properties":{"valid":{"type":"boolean","title":"Valid"},"result_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Result Type","description":"number, currency, text, checkbox, date or timestamp."},"currency_code":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Currency Code"},"depends_on":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Depends On"},"referenced_object_slugs":{"items":{"type":"string"},"type":"array","title":"Referenced Object Slugs"},"errors":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Errors","description":"Field-level problems (`reason` is a stable code)."},"preview_value":{"title":"Preview Value"},"preview_error":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Preview Error","description":"Why the preview record could not be evaluated (a code, never a value)."},"preview_rollups":{"items":{"$ref":"#/components/schemas/PreviewRollup"},"type":"array","title":"Preview Rollups","description":"With a preview record: one entry per rollup in the expression, counted over the records the caller may read."}},"type":"object","required":["valid"],"title":"FormulaValidateResponse"},"GapNote":{"properties":{"component":{"type":"string","title":"Component"},"kind":{"type":"string","const":"no_history","title":"Kind","default":"no_history"},"records":{"type":"integer","title":"Records"}},"type":"object","required":["component","records"],"title":"GapNote"},"GenerateAllDocumentsRequest":{"properties":{"website_url":{"type":"string","title":"Website Url","description":"The company website every document is generated against. Intelligence data must already exist for it."}},"type":"object","required":["website_url"],"title":"GenerateAllDocumentsRequest","description":"Mirrors `campaign_builder.routers.global_context.GenerateAllDocumentsRequest`.\n\nONE-SHOT. The app refuses this with a 409 once a pipeline has completed for\nthe org, which is why `POST /global-context/regenerate` exists - use that\nto rebuild documents that already exist."},"GenerateAllReportsRequest":{"properties":{"website_url":{"type":"string","title":"Website Url"}},"type":"object","required":["website_url"],"title":"GenerateAllReportsRequest","description":"Address the whole six-report workflow for one website."},"GenerateAppPageRequest":{"properties":{"instruction":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Instruction","description":"What the page should show. Free text; the generator composes every bound source."}},"type":"object","title":"GenerateAppPageRequest"},"GenerateAppPageResponse":{"properties":{"page_id":{"type":"string","title":"Page Id"},"job_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Id"},"status":{"type":"string","title":"Status","default":"generating"}},"type":"object","required":["page_id"],"title":"GenerateAppPageResponse"},"GenerateFilterRequest":{"properties":{"prompt":{"type":"string","title":"Prompt"},"source_list_id":{"type":"integer","title":"Source List Id"}},"type":"object","required":["prompt","source_list_id"],"title":"GenerateFilterRequest","description":"Turn a sentence into a routing filter."},"GenerateQueryRequest":{"properties":{"listener_type":{"type":"string","enum":["brand","competitor","keyword","engagement","user"],"title":"Listener Type"},"description":{"type":"string","maxLength":1000,"minLength":1,"title":"Description"}},"type":"object","required":["listener_type","description"],"title":"GenerateQueryRequest","description":"Turn a plain-English description into a platform-native query.\n\nTHIS SPENDS CREDITS - it is an LLM call. It returns the query rather than\ncreating a listener, so you can read it before committing to one."},"GenerateReportRequest":{"properties":{"website_url":{"type":"string","title":"Website Url"},"report_number":{"type":"integer","title":"Report Number"},"report_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Report Type"}},"type":"object","required":["website_url","report_number"],"title":"GenerateReportRequest","description":"Generate ONE research report. SPENDS CREDIT - a long multi-pass run."},"GenerateSpintaxRequest":{"properties":{"subject":{"type":"string","maxLength":2000,"minLength":1,"title":"Subject","description":"Email subject to rewrite into spintax"},"body":{"type":"string","maxLength":50000,"minLength":1,"title":"Body","description":"Email body to rewrite into spintax"},"email_type":{"type":"string","enum":["plain","html"],"title":"Email Type","description":"Body format. 'html' preserves every <a href> link and all {{variables}} in the rewrite.","default":"plain"},"tone_instructions":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Tone Instructions","description":"Optional tone/style guidance applied during the rewrite (e.g. 'casual, no exclamation marks')."},"strength":{"type":"string","enum":["light","balanced","maximum"],"title":"Strength","description":"Variation intensity: how heavily to vary the copy and how deeply to nest spintax blocks. Each level carries an ENFORCED ceiling on total distinct renderings (subject x body), applied after generation: 'light' up to 200 (flat blocks only), 'balanced' up to 5,000, 'maximum' up to 100,000. Output over the ceiling is trimmed down, never rejected.","default":"balanced"}},"type":"object","required":["subject","body"],"title":"GenerateSpintaxRequest","description":"One-time AI generation: rewrite a manual email into spintax.\n\nField types intentionally mirror the internal\n``sequencer.interfaces.voice.email_generation.GenerateSpintaxPayload``\n(same Literals) so outer/inner validation cannot drift. The legacy\n``target_combinations`` knob is deliberately NOT exposed on the public\nsurface; ``strength`` supersedes it."},"GenerateSpintaxResponse":{"properties":{"subject":{"type":"string","title":"Subject","description":"Subject rewritten with {{option a|option b}} spintax blocks"},"body":{"type":"string","title":"Body","description":"Body rewritten with (possibly nested) spintax blocks"},"subject_combinations":{"type":"integer","title":"Subject Combinations","description":"Distinct renderings the subject can produce"},"body_combinations":{"type":"integer","title":"Body Combinations","description":"Distinct renderings the body can produce"},"total_combinations":{"type":"integer","title":"Total Combinations","description":"Distinct full-email renderings (subject x body)"}},"type":"object","required":["subject","body","subject_combinations","body_combinations","total_combinations"],"title":"GenerateSpintaxResponse","description":"Spintax-encoded email plus its distinct-rendering counts."},"GenerateStepTemplatesRequest":{"properties":{"agent_name":{"type":"string","title":"Agent Name","description":"The agent whose voice and context the drafts use."}},"type":"object","required":["agent_name"],"title":"GenerateStepTemplatesRequest","description":"Ask an agent to draft step content. Mirrors `GetContentTemplatesParams`."},"GenerateTrackedLinksRequest":{"properties":{"destination_url":{"type":"string","title":"Destination Url","description":"Absolute http(s) URL every link points at."},"link_name":{"type":"string","title":"Link Name","description":"What this set of links is called."},"column_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Column Title","description":"Column to write the links into."},"params_template":{"additionalProperties":{"type":"string"},"type":"object","title":"Params Template","description":"Query parameters to interpolate per row, e.g. {'utm_term': '{company}'}."},"shorten":{"type":"boolean","title":"Shorten","description":"Use the short-link domain.","default":false},"placement":{"type":"string","enum":["fragment","query"],"title":"Placement","description":"Where the token goes on a NON-shortened URL: `fragment` (#t=…) or `query` (?g8t=…). Ignored when `shorten` is on.","default":"fragment"},"stream_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stream Id"}},"type":"object","required":["destination_url","link_name"],"title":"GenerateTrackedLinksRequest","description":"Mint one tracked URL per row, into a column on the list."},"GenerateVideoClipRequest":{"properties":{"prompt_inputs":{"$ref":"#/components/schemas/VideoClipPromptInputs"},"prompt_final":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Prompt Final"},"duration_seconds":{"type":"integer","enum":[4,6,8],"title":"Duration Seconds","default":8},"aspect_ratio":{"type":"string","enum":["16:9","9:16"],"title":"Aspect Ratio","default":"16:9"},"start_image_url":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Start Image Url"},"reference_image_urls":{"items":{"type":"string"},"type":"array","maxItems":3,"title":"Reference Image Urls"},"creative_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Creative Id"}},"type":"object","required":["prompt_inputs"],"title":"GenerateVideoClipRequest","description":"Generate one video clip. SPENDS CREDIT - priced per second of footage."},"GetFieldValueResponse":{"properties":{"column_id":{"type":"integer","title":"Column Id"},"record_id":{"type":"integer","title":"Record Id"},"entity":{"type":"string","title":"Entity"},"name":{"type":"string","title":"Name","description":"The underlying column slug (column_name_db)."},"value":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Value","description":"The stored value as text, or null if the column is unset for this row. Number and yes/no columns are returned in text form ('42', '12.5', 'true'/'false'); read `typed_value` for the native JSON value."},"data_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Data Type","description":"The column's data type, the same value `GET /fields` reports in `data_type`: 'text', 'int', 'numeric' or 'boolean'."},"typed_value":{"anyOf":[{"type":"boolean"},{"type":"integer"},{"type":"number"},{"type":"string"},{"type":"null"}],"title":"Typed Value","description":"The stored value in its native JSON type: a number for 'int' and 'numeric' columns, true/false for 'boolean' columns, a string for text columns. Null when the column is unset for this row."}},"type":"object","required":["column_id","record_id","entity","name"],"title":"GetFieldValueResponse","description":"Response body for reading a single custom column value from one row."},"GetOrCreateCrmListRequest":{"properties":{"name":{"type":"string","title":"Name","description":"List name. Matched in the CRM; created when absent."},"connection_id":{"type":"string","title":"Connection Id"},"entity_type":{"anyOf":[{"type":"string","enum":["contacts","companies","deals","leads"]},{"type":"null"}],"title":"Entity Type","description":"Which object the list holds. Omit for `contacts`."}},"type":"object","required":["name","connection_id"],"title":"GetOrCreateCrmListRequest","description":"Get, or create, a list in the CUSTOMER'S CRM, matched by name.\n\nNot a mirror - the app takes these three as QUERY parameters on a POST,\nwhich is not a shape to publish. The field names and meanings are the\nhandler's."},"GlobalContextGenerateRequest":{"properties":{"doc_type":{"type":"string","title":"Doc Type","description":"Must match the `doc_type` in the path."},"website_url":{"type":"string","title":"Website Url"}},"type":"object","required":["doc_type","website_url"],"title":"GlobalContextGenerateRequest"},"GradeDraftRequest":{"properties":{"thread_id":{"type":"string","maxLength":2048,"minLength":1,"title":"Thread Id","description":"Email thread id (the `id` from `GET /inbox`)."},"draft_text":{"type":"string","maxLength":20000,"minLength":1,"title":"Draft Text","description":"Plain-text reply draft."}},"type":"object","required":["thread_id","draft_text"],"title":"GradeDraftRequest","description":"Grade an unsent reply against its thread."},"GradingBucketFilterGroupDto":{"properties":{"in":{"items":{"type":"string","enum":["high","med","low"]},"type":"array","maxItems":1000,"title":"In"},"not":{"type":"boolean","title":"Not","default":false}},"additionalProperties":false,"type":"object","title":"GradingBucketFilterGroupDto","description":"`grading_bucket` — a CLOSED vocabulary (`GRADING_BUCKETS`). An unknown\nbucket produces no band clause and widens to the full book."},"GridPageRequest":{"properties":{"offset":{"type":"integer","title":"Offset","default":0},"limit":{"type":"integer","title":"Limit","default":100},"filter_spec":{"anyOf":[{"$ref":"#/components/schemas/FilterSpec"},{"type":"null"}]},"order_spec":{"anyOf":[{"$ref":"#/components/schemas/OrderSpec"},{"type":"null"}]},"sort_model":{"anyOf":[{"items":{"additionalProperties":{"type":"string"},"type":"object"},"type":"array"},{"type":"null"}],"title":"Sort Model"},"valid_phones_only":{"type":"boolean","title":"Valid Phones Only","default":false},"include_contact_data":{"type":"boolean","title":"Include Contact Data","default":false}},"type":"object","title":"GridPageRequest","description":"Mirrors `GridPageRequest`. A read - it paginates the queue grid."},"GroupTarget":{"properties":{"kind":{"type":"string","const":"group","title":"Kind","default":"group"},"values":{"items":{},"type":"array","maxItems":3,"title":"Values"},"gaps":{"items":{"anyOf":[{"type":"string","const":"no_history"},{"type":"null"}]},"type":"array","maxItems":3,"title":"Gaps"}},"additionalProperties":false,"type":"object","title":"GroupTarget","description":"One row of a table, bar or line report: the group values in dimension order. ``gaps[i]`` is\n``\"no_history\"`` when dimension *i* is the history-gap group of an as-of report. A numeric value a JSON number\ncannot carry exactly (past 15 significant digits) is its exact decimal text here; echo the target unchanged."},"GroupValue":{"properties":{"id":{"type":"string","title":"Id"},"value":{"title":"Value"},"gap":{"anyOf":[{"type":"string","const":"no_history"},{"type":"null"}],"title":"Gap"}},"type":"object","required":["id"],"title":"GroupValue"},"GtmLibraryListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"GtmLibraryListPayload","description":"A list of personas, ICPs or committees under `items`."},"GtmLibraryPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"GtmLibraryPayload","description":"A persona, ICP, TAM definition or buying committee, as the app returns it."},"HTTPValidationError":{"properties":{"detail":{"items":{"$ref":"#/components/schemas/ValidationError"},"type":"array","title":"Detail"}},"type":"object","title":"HTTPValidationError"},"HandoffPoolScopeRequest":{"properties":{"chat_bot_ids":{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":200,"title":"Chat Bot Ids"}},"type":"object","title":"HandoffPoolScopeRequest","description":"The COMPLETE new bot scope. Empty list = every bot; bots left out are dropped."},"HandoffPoolTeamsRequest":{"properties":{"team_ids":{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":200,"minItems":1,"title":"Team Ids"},"pool":{"type":"string","enum":["external","internal"],"title":"Pool","default":"external"},"chat_bot_ids":{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":200,"title":"Chat Bot Ids"}},"type":"object","required":["team_ids"],"title":"HandoffPoolTeamsRequest","description":"Teams to add to the handoff pool. Same bot-scoping rules as people."},"HandoffPoolUsersRequest":{"properties":{"user_ids":{"items":{"type":"string"},"type":"array","maxItems":200,"minItems":1,"title":"User Ids"},"pool":{"type":"string","enum":["external","internal"],"title":"Pool","default":"external"},"chat_bot_ids":{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":200,"title":"Chat Bot Ids"}},"type":"object","required":["user_ids"],"title":"HandoffPoolUsersRequest","description":"People to add to the handoff pool.\n\n`chat_bot_ids` empty means EVERY bot. Non-empty is valid only for the\n`external` pool - the internal pool is not per-bot, and the app refuses\nthe combination with a 422. Both lists are capped at 200 by the app to\nbound the per-person-per-bot rows one call can write."},"HangupCallRequest":{"properties":{"session_id":{"type":"string","title":"Session Id"},"call_id":{"type":"string","title":"Call Id"}},"type":"object","required":["session_id","call_id"],"title":"HangupCallRequest","description":"Mirrors `HangupCallRequest`. Ends a call already in progress."},"HeadcountFilterGroupDto":{"properties":{"in":{"items":{"type":"string","enum":["1-10","11-50","51-200","201-1000","1001+"]},"type":"array","maxItems":1000,"title":"In"},"not":{"type":"boolean","title":"Not","default":false}},"additionalProperties":false,"type":"object","title":"HeadcountFilterGroupDto","description":"`headcount` — a CLOSED vocabulary (`HEADCOUNT_BANDS`), and the exact list\n`/filter-options` hands the client."},"HiddenCustomFieldsPatchRequest":{"properties":{"hidden_custom_fields":{"items":{"type":"string"},"type":"array","title":"Hidden Custom Fields"}},"type":"object","required":["hidden_custom_fields"],"title":"HiddenCustomFieldsPatchRequest","description":"Mirrors `HiddenCustomFieldsPatchRequest`. Display only."},"HireOfferAcceptedTerm":{"properties":{"document_id":{"type":"string","title":"Document Id","description":"marketplace-terms | sdr-participation-agreement"}},"type":"object","required":["document_id"],"title":"HireOfferAcceptedTerm","description":"One T&C document the client agreed to when sending the offer.\n\nMirrors ``AcceptedTermDTO`` in ``marketplace.interfaces.fastapi.dtos``:\nonly ``document_id`` is sent; the server resolves the current\nversion + URL server-side at send time."},"HireSdrRequest":{"properties":{"sdr_id":{"type":"string","title":"Sdr Id"},"monthly_rate_usd":{"anyOf":[{"type":"number","minimum":0.0},{"type":"string"}],"title":"Monthly Rate Usd","default":"0"},"per_meeting_rate_usd":{"anyOf":[{"type":"number","minimum":0.0},{"type":"string"}],"title":"Per Meeting Rate Usd","default":"0"},"start_date":{"type":"string","title":"Start Date","description":"YYYY-MM-DD"},"contract_length_months":{"anyOf":[{"type":"integer","maximum":120.0,"minimum":1.0},{"type":"null"}],"title":"Contract Length Months","description":"None = month-to-month (default); otherwise number of months"},"commission_plan_version_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Commission Plan Version Id"},"scope_text":{"anyOf":[{"type":"string","maxLength":4000},{"type":"null"}],"title":"Scope Text","description":"Optional scope-of-engagement text shown on the contract"},"accepted_terms":{"items":{"$ref":"#/components/schemas/HireOfferAcceptedTerm"},"type":"array","title":"Accepted Terms","description":"Required: client's acceptance of the Marketplace Terms + SDR Participation Agreement. An empty list is rejected with 400 (terms_not_accepted) by the underlying hire handler."}},"type":"object","required":["sdr_id","start_date"],"title":"HireSdrRequest","description":"Hire-offer body — mirrors the Phase B ``HireSdrRequest`` in\n``marketplace.interfaces.fastapi.dtos``.\n\nPhase B removed ``hiring_fee_usd`` and ``commission_percentage`` and added\n``contract_length_months``, ``scope_text`` and the required\n``accepted_terms``. The contract is generated + e-signed inside graph8,\nand the client's T&C acceptance is captured in the same transaction as the\nhiring row — so ``accepted_terms`` must be non-empty or the underlying\nhandler returns ``terms_not_accepted`` (400)."},"HostLimitKindRequest":{"properties":{"mode":{"type":"string","enum":["inherit","custom","none"],"title":"Mode"},"limits":{"anyOf":[{"additionalProperties":{"type":"integer"},"type":"object"},{"type":"null"}],"title":"Limits"}},"additionalProperties":false,"type":"object","required":["mode"],"title":"HostLimitKindRequest","description":"One limit kind of a host's own limit: inherit the default, a custom value, or none."},"HotContact":{"properties":{"contact_id":{"type":"string","title":"Contact Id"},"who":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Who","description":"Display name, else email, else id"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"},"events":{"type":"integer","title":"Events","description":"Inbound interaction events in the window","default":0},"meetings":{"type":"integer","title":"Meetings","description":"Of those events, how many were meetings","default":0},"last_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last At","description":"Most recent inbound activity (ISO)"}},"type":"object","required":["contact_id"],"title":"HotContact","description":"One most-engaged contact (ranked by recent inbound activity)."},"HotContactsResult":{"properties":{"days":{"type":"integer","title":"Days"},"contacts":{"items":{"$ref":"#/components/schemas/HotContact"},"type":"array","title":"Contacts"}},"type":"object","required":["days"],"title":"HotContactsResult"},"HumanAvailabilityRequest":{"properties":{"enabled":{"type":"boolean","title":"Enabled","default":false},"timezone":{"type":"string","maxLength":64,"minLength":1,"title":"Timezone","description":"IANA zone the intervals are expressed in.","default":"UTC"},"intervals":{"items":{"$ref":"#/components/schemas/AvailabilityInterval"},"type":"array","title":"Intervals","description":"Weekly windows: `{day: 0-6, start: 'HH:MM', end: 'HH:MM'}`."},"overrides":{"items":{"$ref":"#/components/schemas/AvailabilityOverride"},"type":"array","title":"Overrides","description":"Date overrides: `{date: 'YYYY-MM-DD', intervals: [...]}`."},"chat_bot_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Chat Bot Id","description":"Bot this schedule applies to. NULL is the org default."},"surface":{"anyOf":[{"type":"string","enum":["external","internal"]},{"type":"null"}],"title":"Surface"}},"type":"object","title":"HumanAvailabilityRequest","description":"When a human is available to take a handed-off conversation.\n\nTHIS IS WHAT DECIDES WHETHER A VISITOR IS OFFERED A PERSON. Turning it on\nwith no reachable interval is worse than leaving it off: the widget offers\na handover nobody answers. The app refuses the unreachable shapes; this\nforwards its answer.\n\n`intervals` and `overrides` use the app's own window models, which reject a\nzero-length window and refuse overlapping ones - see the module docstring."},"IcpGenerateRequest":{"properties":{"website_url":{"type":"string","title":"Website Url","description":"The website the ICPs are researched from."},"save_to_database":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Save To Database","description":"Persist the generated ICPs.","default":true}},"type":"object","required":["website_url"],"title":"IcpGenerateRequest"},"ImageAltTextRequest":{"properties":{"alt_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Alt Text"}},"type":"object","title":"ImageAltTextRequest","description":"Set alt text, which is ALSO the library display name."},"ImageCategoryRequest":{"properties":{"category":{"type":"string","title":"Category"}},"type":"object","required":["category"],"title":"ImageCategoryRequest","description":"Recategorise an image. Categories come from `GET /image-library/categories`."},"ImageFeedbackRequest":{"properties":{"feedback":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Feedback"}},"type":"object","title":"ImageFeedbackRequest","description":"Thumbs up/down on an image. Null clears the existing feedback."},"ImageMergeDuplicatesRequest":{"properties":{"keeper_id":{"type":"string","format":"uuid","title":"Keeper Id"},"duplicate_ids":{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":100,"minItems":1,"title":"Duplicate Ids"}},"type":"object","required":["keeper_id","duplicate_ids"],"title":"ImageMergeDuplicatesRequest","description":"Keep one image; remove the duplicates after re-pointing their references."},"ImagePointEditRequest":{"properties":{"x":{"type":"number","maximum":100000.0,"minimum":0.0,"title":"X"},"y":{"type":"number","maximum":100000.0,"minimum":0.0,"title":"Y"},"instruction":{"type":"string","maxLength":500,"minLength":1,"title":"Instruction"}},"type":"object","required":["x","y","instruction"],"title":"ImagePointEditRequest","description":"Pin a point on the image and say what changes there. SPENDS CREDIT."},"ImageTagsRequest":{"properties":{"tags":{"items":{"type":"string"},"type":"array","title":"Tags"}},"type":"object","required":["tags"],"title":"ImageTagsRequest","description":"The image's complete new tag set. Send `[]` to clear it."},"ImportAudienceRequest":{"properties":{"audience_id":{"type":"integer","title":"Audience Id","description":"Integer audience id, not a UUID."}},"type":"object","required":["audience_id"],"title":"ImportAudienceRequest","description":"Bulk-import an audience list's contacts as subscribers."},"ImportCompaniesRequest":{"properties":{"source":{"type":"string","title":"Source","description":"Where the records came from, recorded on the import."},"contacts":{"items":{"$ref":"#/components/schemas/CompanyContactImport"},"type":"array","title":"Contacts","description":"Contacts to import."}},"type":"object","required":["source","contacts"],"title":"ImportCompaniesRequest","description":"Create or update companies from a batch of contacts.\n\nGrouping is by email domain: a new domain creates a company, a known one\nis updated in place. There is no separate \"company\" payload."},"ImportContactsRequest":{"properties":{"list_id":{"type":"integer","title":"List Id","description":"Audience list the contacts land in. REQUIRED - an import with no destination has nowhere to put the rows, and the caller needs WRITE access to this list, not just read."},"column_mapping":{"additionalProperties":{"type":"string"},"type":"object","title":"Column Mapping","description":"Source column -> graph8 field. An EMPTY mapping is legal and means the importer falls back to its own header matching, which is why this is not required - but an unmapped column the importer cannot recognise is dropped silently, so preview first."},"update_policy":{"type":"string","enum":["autofill","override"],"title":"Update Policy","description":"What happens when a row matches an existing contact. `override` replaces the field; `autofill` only fills one that is currently EMPTY. The default is `override`, matching the app - so an import run without thinking about this WILL overwrite existing data.","default":"override"},"enrich_from_graph8":{"type":"boolean","title":"Enrich From Graph8","description":"Match imported rows against the graph8 index and fill missing fields - contacts by work email or LinkedIn URL, companies by domain. Off by default because it is extra work the caller may not want on a file they already trust.","default":false}},"type":"object","required":["list_id"],"title":"ImportContactsRequest","description":"Import a previously uploaded file's rows as contacts into one list."},"ImportContactsResponse":{"properties":{"imported":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Imported"},"updated":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Updated"},"skipped":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Skipped"},"failed":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Failed"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"}},"additionalProperties":true,"type":"object","title":"ImportContactsResponse","description":"What the import actually did."},"ImportFindPeopleRequest":{"properties":{"company_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Company Ids","description":"Import results for these companies. OMIT to import ALL pending."},"result_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Result Ids","description":"Specific results. Overrides `company_ids` when given."},"destination_list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Destination List Id"}},"type":"object","title":"ImportFindPeopleRequest","description":"Import search results into the destination list."},"ImportHtmlRequest":{"properties":{"html":{"type":"string","maxLength":2000000,"minLength":16,"title":"Html"},"strip_vendor_css":{"type":"boolean","title":"Strip Vendor Css","default":false},"reassign_g8_ids":{"type":"boolean","title":"Reassign G8 Ids","default":false},"reinfer_button_actions":{"type":"boolean","title":"Reinfer Button Actions","default":false},"confirm_action_rebuild":{"type":"boolean","title":"Confirm Action Rebuild","default":false},"commit":{"type":"boolean","title":"Commit","description":"False previews; true writes the draft.","default":false}},"type":"object","required":["html"],"title":"ImportHtmlRequest","description":"Import externally edited HTML into a draft. Spends nothing.\n\n`commit` false is a DRY RUN that reports what the import would change.\n`reassign_g8_ids` renumbers the element ids every other edit route\naddresses, which invalidates ids a caller is holding - the app requires\n`confirm_action_rebuild` alongside it for exactly that reason."},"ImportMeetingRequest":{"properties":{"provider":{"type":"string","enum":["google_calendar","office365_calendar"],"title":"Provider"},"calendar_id":{"type":"string","title":"Calendar Id"},"event_id":{"type":"string","title":"Event Id"},"event_type_id":{"type":"integer","title":"Event Type Id","description":"The graph8 event type to import it as."}},"type":"object","required":["provider","calendar_id","event_id","event_type_id"],"title":"ImportMeetingRequest","description":"Pull a meeting that was booked OUTSIDE graph8 into the bookings list.\n\nIDENTIFIERS ONLY, exactly as the app's model is - no title, times or\nattendees. Those are re-read server-side from the caller's own calendar\ncredential; accepting them from the request would let a caller fabricate a\n\"meeting\" and have it stored as fact, counted in reporting and blocking\nreal availability."},"ImportPage":{"properties":{"revision":{"type":"integer","minimum":1.0,"title":"Revision","description":"The draft revision this page was planned against"},"offset":{"type":"integer","maximum":4999.0,"minimum":0.0,"title":"Offset","default":0},"limit":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Limit","default":100}},"additionalProperties":false,"type":"object","required":["revision"],"title":"ImportPage"},"ImportPreviewRow":{"properties":{"row_number":{"type":"integer","minimum":2.0,"title":"Row Number"},"record_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Record Id"},"revision":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Revision"},"values":{"additionalProperties":true,"type":"object","title":"Values"},"errors":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Errors"},"already_imported":{"type":"boolean","title":"Already Imported","default":false}},"type":"object","required":["row_number"],"title":"ImportPreviewRow"},"ImportReceiptRow":{"properties":{"row_number":{"type":"integer","title":"Row Number"},"record_id":{"type":"string","format":"uuid","title":"Record Id"},"revision":{"type":"integer","title":"Revision"},"action":{"type":"string","enum":["created","updated"],"title":"Action"},"replayed":{"type":"boolean","title":"Replayed","default":false}},"type":"object","required":["row_number","record_id","revision","action"],"title":"ImportReceiptRow"},"ImportRowExpectation":{"properties":{"row_number":{"type":"integer","minimum":2.0,"title":"Row Number"},"record_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Record Id"},"revision":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Revision"}},"additionalProperties":false,"type":"object","required":["row_number"],"title":"ImportRowExpectation"},"ImportSitemapRequest":{"properties":{"sitemap_url":{"type":"string","title":"Sitemap Url"},"url_must_contain":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Url Must Contain"},"url_must_not_contain":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Url Must Not Contain"}},"type":"object","required":["sitemap_url"],"title":"ImportSitemapRequest","description":"Import pages from a sitemap. Fetches the sitemap; spends no credit.\n\nThe two filters are substring matches applied to each discovered URL."},"ImportSkippedRow":{"properties":{"row_number":{"type":"integer","title":"Row Number"},"errors":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Errors"}},"type":"object","required":["row_number","errors"],"title":"ImportSkippedRow","description":"A row this commit did not import; its errors are kept for the error file."},"ImproveIdeaRequest":{"properties":{"idea":{"type":"string","title":"Idea","description":"The raw idea to rewrite into a fuller brief."}},"type":"object","required":["idea"],"title":"ImproveIdeaRequest","description":"Mirrors `campaign_builder.routers.brand_kit.ImproveIdeaRequest`."},"ImproveInstructionRequest":{"properties":{"user_instruction":{"type":"string","minLength":1,"title":"User Instruction","description":"What the drafting agent should do, in the author's own words."},"old_instruction":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Old Instruction","description":"The instruction being replaced, so the rewrite keeps its intent."}},"additionalProperties":false,"type":"object","required":["user_instruction"],"title":"ImproveInstructionRequest","description":"Rewrite a step's drafting instruction. Mirrors `PromptImprovementPayload`."},"InboundRouteCreateRequest":{"properties":{"phone_number":{"type":"string","minLength":1,"title":"Phone Number","description":"The number this rule applies to."},"priority":{"type":"integer","title":"Priority","description":"Lower wins. Ties are resolved arbitrarily.","default":100},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"match_conditions":{"additionalProperties":true,"type":"object","title":"Match Conditions","description":"`{\"always\": true}` or a `{\"schedule\": {...}}` block with `days`, `start_time`/`end_time` as HH:MM, and an IANA `timezone`."},"target_type":{"type":"string","enum":["ai_agent","department","extension","voicemail"],"title":"Target Type"},"target_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Id","description":"Agent id, department or extension - depends on `target_type`."},"ring_strategy":{"type":"string","enum":["single","round_robin"],"title":"Ring Strategy","default":"single"},"queue_max_wait_seconds":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Queue Max Wait Seconds"},"is_active":{"type":"boolean","title":"Is Active","default":true}},"type":"object","required":["phone_number","target_type"],"title":"InboundRouteCreateRequest","description":"A rule deciding where an inbound call on one number goes.\n\n`org_id` is absent on purpose - pinned from the key by the router.\nRules are evaluated by ascending `priority`; the first whose\n`match_conditions` hold wins."},"InboundRouteUpdateRequest":{"properties":{"priority":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Priority"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"match_conditions":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Match Conditions"},"target_type":{"anyOf":[{"type":"string","enum":["ai_agent","department","extension","voicemail"]},{"type":"null"}],"title":"Target Type"},"target_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Id"},"ring_strategy":{"anyOf":[{"type":"string","enum":["single","round_robin"]},{"type":"null"}],"title":"Ring Strategy"},"queue_max_wait_seconds":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Queue Max Wait Seconds"},"is_active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Active"}},"type":"object","title":"InboundRouteUpdateRequest","description":"Partial update of one rule. Omitted fields are untouched."},"InboxAgentCreateRequest":{"properties":{"name":{"type":"string","title":"Name","description":"Unique within the organisation."}},"type":"object","required":["name"],"title":"InboxAgentCreateRequest","description":"Create an AI Inbox agent.\n\nNOT the Copilot Agent Runtime at `/agent/*` - that surface runs and\napproves autonomous work. This is the named responder an inbox tag or an\nemail setting points at."},"InboxChannel":{"type":"string","enum":["email","sms","linkedin"],"title":"InboxChannel"},"InboxListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"InboxListPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape."},"InboxMessageItem":{"properties":{"message_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Message Id"},"from_address":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"From Address"},"to_addresses":{"items":{"type":"string"},"type":"array","title":"To Addresses"},"content":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Content"},"responder":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Responder","description":"USER, AI, or OTHER"},"date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Date"},"is_draft":{"type":"boolean","title":"Is Draft","default":false}},"type":"object","title":"InboxMessageItem"},"InboxOpsListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"InboxOpsListPayload","description":"An open LIST envelope: a bare list, or a named list, is reachable as\n`items`, and every other key the app returned (totals, pagination) is kept."},"InboxPage":{"properties":{"items":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Items"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"InboxPage","description":"A page of threads, or one thread, exactly as the inbox returns it."},"InboxPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"InboxPayload","description":"An open envelope for a comment, an assignment or a workspace.\n\nOpen because a comment carries attachment refs and mention metadata that\ngrow, and because an assignment result reports per-assignee outcomes."},"InboxThreadResponse":{"properties":{"id":{"type":"string","title":"Id"},"channel":{"type":"string","title":"Channel"},"subject":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subject"},"contact":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Contact","description":"Contact snapshot: name, email, company"},"messages":{"items":{"$ref":"#/components/schemas/InboxMessageItem"},"type":"array","title":"Messages"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"tags":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Tags"},"assignees":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Assignees"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"},"mailbox":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mailbox","description":"Email: the connected mailbox this thread belongs to. A reply goes out from it by default, so pass it as `from_address` (or omit `from_address`) on POST /inbox/{id}/send."},"from_number":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"From Number","description":"SMS: your number the thread runs on; the default `from_address` for an SMS reply."},"to_number":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"To Number","description":"SMS: the contact's number; the default `to` for an SMS reply."},"linkedin_account_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Linkedin Account Id","description":"LinkedIn: the sending account; the default `from_address` for a LinkedIn reply."}},"type":"object","required":["id","channel"],"title":"InboxThreadResponse"},"InfrastructureProfileUpdateRequest":{"properties":{"selections":{"additionalProperties":{"$ref":"#/components/schemas/OrgInfrastructureSelection"},"type":"object","title":"Selections","description":"Category id -> selection."}},"type":"object","required":["selections"],"title":"InfrastructureProfileUpdateRequest"},"InlineAIConfig":{"properties":{"kind":{"type":"string","const":"ai","title":"Kind"},"prompt":{"type":"string","maxLength":20000,"minLength":10,"title":"Prompt"},"outputs":{"items":{"$ref":"#/components/schemas/InlineOutputField"},"type":"array","maxItems":10,"minItems":1,"title":"Outputs"},"model":{"type":"string","maxLength":120,"title":"Model","default":"openai/gpt-4o-mini"},"usecase":{"type":"string","enum":["create-modify-content","content-generation","web-research"],"title":"Usecase","default":"create-modify-content"},"scope":{"anyOf":[{"type":"string","enum":["contact","company"]},{"type":"null"}],"title":"Scope"}},"type":"object","required":["kind","prompt","outputs"],"title":"InlineAIConfig","description":"Create a new AI column as part of saving the pipeline."},"InlineOutputField":{"properties":{"name":{"type":"string","maxLength":50,"minLength":1,"pattern":"^[a-z][a-z0-9_]*$","title":"Name"},"type":{"type":"string","enum":["Text","Number","Boolean"],"title":"Type","default":"Text"}},"type":"object","required":["name"],"title":"InlineOutputField"},"InlineQualificationConfig":{"properties":{"kind":{"type":"string","const":"qualification","title":"Kind"},"entity":{"type":"string","enum":["company","contact"],"title":"Entity"},"template_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Template Id"}},"type":"object","required":["kind","entity"],"title":"InlineQualificationConfig","description":"Add a qualification column from a template."},"InlineWaterfallConfig":{"properties":{"kind":{"type":"string","const":"waterfall","title":"Kind"},"target_column":{"type":"string","maxLength":120,"minLength":1,"title":"Target Column"},"verify":{"type":"boolean","title":"Verify","default":false}},"type":"object","required":["kind","target_column"],"title":"InlineWaterfallConfig","description":"Add a waterfall that fills an existing column."},"InmailPrepareRequest":{"properties":{"contact_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array","maxItems":500,"minItems":1},{"type":"null"}],"title":"Contact Ids","description":"Contacts to prepare; omit for every contact on the sequence's list."}},"type":"object","title":"InmailPrepareRequest"},"InstallAppRequest":{"properties":{"app_id":{"type":"string","title":"App Id","description":"The app to install, e.g. `dapp_a1b2c3d4e5f6`."},"scopes":{"items":{"type":"string"},"type":"array","maxItems":32,"title":"Scopes","description":"Scopes you grant the app, e.g. `objects:read`. Only scopes the platform enables for apps are accepted; anything else is rejected rather than silently dropped, so a granted scope always means what it says."}},"type":"object","required":["app_id"],"title":"InstallAppRequest","description":"A client workspace consenting to an app."},"InstallationResponse":{"properties":{"install_id":{"type":"string","title":"Install Id"},"app_id":{"type":"string","title":"App Id"},"client_org_id":{"type":"string","title":"Client Org Id"},"status":{"type":"string","title":"Status","description":"`pending`, `consented`, `revoked`, `suspended` or `expired`."},"consented_scopes":{"items":{"type":"string"},"type":"array","title":"Consented Scopes"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"revoked_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Revoked At"}},"type":"object","required":["install_id","app_id","client_org_id","status"],"title":"InstallationResponse","description":"One client org's install of an app. Mirrors `InstallationDto`."},"InstalledAppResponse":{"properties":{"app_id":{"type":"string","title":"App Id"},"install_id":{"type":"string","title":"Install Id"},"client_org_id":{"type":"string","title":"Client Org Id"},"status":{"type":"string","title":"Status","description":"`pending`, `consented`, `revoked`, `suspended` or `expired`."},"consented_scopes":{"items":{"type":"string"},"type":"array","title":"Consented Scopes"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"revoked_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Revoked At"},"app_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"App Name","description":"The app's display name, when it is still resolvable."},"app_slug":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"App Slug"}},"type":"object","required":["app_id","install_id","client_org_id","status"],"title":"InstalledAppResponse","description":"An app installed in your workspace, and what you granted it."},"InstantiatePipelineTemplateRequest":{"properties":{"template_key":{"type":"string","maxLength":64,"minLength":1,"title":"Template Key"},"qualification_template_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Qualification Template Id"}},"type":"object","required":["template_key"],"title":"InstantiatePipelineTemplateRequest","description":"Build a pipeline from a recipe in `GET /enrichment/lists/pipeline-templates`."},"IntIdFilterGroupDto":{"properties":{"in":{"items":{"type":"string","maxLength":512},"type":"array","maxItems":1000,"title":"In"},"not":{"type":"boolean","title":"Not","default":false}},"additionalProperties":false,"type":"object","title":"IntIdFilterGroupDto","description":"`rec_type` / `audiences` — `Lead.rec_type` is `SmallInteger` and\n`audience_id` is `Integer`; both appliers coerce and skip what will not\nparse."},"IntegrationCredentialTest":{"properties":{"api_key":{"type":"string","minLength":1,"title":"Api Key","description":"The token to try. Not stored."}},"type":"object","required":["api_key"],"title":"IntegrationCredentialTest","description":"voice `WorkflowIntegrationTestRequest`."},"IntegrationOpPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"IntegrationOpPayload","description":"An open envelope for one result."},"IntegrationStatusPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"IntegrationStatusPayload","description":"An integration's connection state, a test result, or a folder listing."},"IntegrityCheckRequest":{"properties":{"extra_fields":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Extra Fields","description":"Enrichment / AI / dynamic columns to measure on top of the default fields - the `column_name_db` values from `GET /lists/{list_id}/data-columns`."}},"type":"object","title":"IntegrityCheckRequest","description":"Which fields to measure. Mirrors the app's `IntegrityCheckRequest`."},"IntelligenceAnalyzeRequest":{"properties":{"website_url":{"type":"string","title":"Website Url","description":"The company website to research."},"force":{"type":"boolean","title":"Force","description":"Re-run even when a recent analysis exists.","default":false}},"type":"object","required":["website_url"],"title":"IntelligenceAnalyzeRequest"},"IntelligenceBrandSuggestionsRequest":{"properties":{"website_url":{"type":"string","maxLength":500,"minLength":3,"title":"Website Url"}},"type":"object","required":["website_url"],"title":"IntelligenceBrandSuggestionsRequest","description":"The organisation's own website, to list the other sites it links to from its homepage."},"IntelligenceDraftAcceptRequest":{"properties":{"website_url":{"type":"string","title":"Website Url"},"field_keys":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Field Keys"}},"type":"object","required":["website_url"],"title":"IntelligenceDraftAcceptRequest","description":"The website, and optionally which fields of the draft to apply (default: every changed field)."},"IntelligenceFieldRequest":{"properties":{"website_url":{"type":"string","title":"Website Url"},"value":{"title":"Value"}},"type":"object","required":["website_url","value"],"title":"IntelligenceFieldRequest","description":"The website the data was collected for, and the FULL edited value of one field."},"IntelligenceListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"IntelligenceListPayload","description":"A list result under `items`."},"IntelligencePayload":{"properties":{},"additionalProperties":true,"type":"object","title":"IntelligencePayload","description":"An intelligence task, data record or document, as the app returns it."},"IntelligenceRetryRequest":{"properties":{"doc_types":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Doc Types","description":"Document types to generate. Omit for the default set."}},"type":"object","title":"IntelligenceRetryRequest","description":"Re-run company intelligence generation. SPENDS CREDITS.\n\nOmitting `doc_types` regenerates the DEFAULT set rather than nothing, so\nan empty body is the expensive option, not the cheap one."},"IntelligenceReviseRequest":{"properties":{"website_url":{"type":"string","title":"Website Url"},"instruction":{"type":"string","maxLength":2000,"minLength":3,"title":"Instruction"}},"type":"object","required":["website_url","instruction"],"title":"IntelligenceReviseRequest","description":"The website and the instruction for the AI rewrite."},"IntelligenceSourceRetryRequest":{"properties":{"website_url":{"type":"string","title":"Website Url"},"data_type":{"type":"string","title":"Data Type","description":"The one data source to re-collect."}},"type":"object","required":["website_url","data_type"],"title":"IntelligenceSourceRetryRequest"},"IntelligenceWebsiteRequest":{"properties":{"website_url":{"type":"string","title":"Website Url"}},"type":"object","required":["website_url"],"title":"IntelligenceWebsiteRequest","description":"The website the intelligence document was collected for."},"IntentPageItem":{"properties":{"url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Url"},"domain_root":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain Root"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"summary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Summary"},"commercial_score":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Commercial Score"},"mention_score":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Mention Score"},"page_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Page Type"},"audience":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience"},"visitors":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Visitors","description":"Distinct visitors (hashed emails) in the lookback window. Set only by pages/search with include_visitors=true when the count succeeded; null otherwise."}},"type":"object","title":"IntentPageItem"},"IntentPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"IntentPayload","description":"One intent object or handler response.\n\nOpen-shaped: these payloads carry corpus detail that grows with the corpus.\nA list result is returned under `items`."},"IntentSignalsResponse":{"properties":{"domain":{"type":"string","title":"Domain"},"score":{"type":"integer","title":"Score","default":0},"intent":{"type":"string","title":"Intent","default":"low"},"signals":{"items":{"type":"string"},"type":"array","title":"Signals","default":[]},"last_seen":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Seen"}},"type":"object","required":["domain"],"title":"IntentSignalsResponse"},"InviteMemberRequest":{"properties":{"email":{"type":"string","maxLength":255,"minLength":3,"title":"Email","description":"Email address to invite. Matched case-insensitively against existing members and invitations."},"role_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Role Id","description":"Id of the role to grant, from `GET /roles`. Mutually exclusive with `role`."},"role":{"anyOf":[{"type":"string","maxLength":100,"minLength":1},{"type":"null"}],"title":"Role","description":"Role slug or display name to grant, resolved within this organisation (slug first, then case-insensitive name). Mutually exclusive with `role_id`."},"list_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"List Ids","description":"List ids to assign. Honoured for the `service_provider` role only, as in the app."}},"type":"object","required":["email"],"title":"InviteMemberRequest","description":"Invite one person into the organisation. Mirrors `roles.InviteUserRequest`\nwith ONE addition: the role may be named instead of identified by UUID.\n\nThe app model takes `role_id: UUID` only, because its caller is a role\npicker that already holds the id. An API caller holds a NAME - \"Engineer\",\n\"Member\" - and making it fetch `GET /roles` first to translate is a round\ntrip this contract can absorb. So exactly one of `role_id` or `role` is\nrequired; `role` is resolved against this organisation's own roles by slug\nfirst, then by case-insensitive display name.\n\n`role` is deliberately NOT defaulted to \"Member\". An absent role on an\ninvitation is a caller mistake, and silently picking the fallback is how\nsomeone ends up in an organisation at a permission level nobody chose."},"InvoiceNotesRequest":{"properties":{"sdr_notes":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sdr Notes"}},"type":"object","title":"InvoiceNotesRequest","description":"Annotate your own draft invoice while it is still in `sdr_review`.\n\n`sdr_notes` is the only field the talent owns - `client_notes` and\n`dispute_reason` belong to the other side of the transaction."},"InvokeActionRequest":{"properties":{"args":{"additionalProperties":true,"type":"object","title":"Args","description":"Action arguments. Validated against the object's own schema; an undeclared field is refused, not dropped."}},"type":"object","title":"InvokeActionRequest"},"InvokeActionResponse":{"properties":{"ok":{"type":"boolean","title":"Ok"},"record_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Record Id"},"message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Message"},"invalidates":{"items":{"type":"string"},"type":"array","title":"Invalidates","description":"Sources whose data is now stale, so a page can refresh only what changed."}},"type":"object","required":["ok"],"title":"InvokeActionResponse"},"IssueAnalyticsKpis":{"properties":{"stale":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Stale"},"last_updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Updated At"},"kpis":{"additionalProperties":true,"type":"object","title":"Kpis"}},"additionalProperties":true,"type":"object","title":"IssueAnalyticsKpis","description":"``GET /{newsletter_id}/issues/{issue_id}/analytics/kpis``. Open dict\nfor the ``kpis`` bucket — bucketed counters evolve independently of\nthis API surface (see ``issue_analytics_router.py`` docstring)."},"IssueCreateRequest":{"properties":{"subject":{"type":"string","maxLength":2000,"title":"Subject"},"preview_text":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Preview Text"},"html_body":{"type":"string","title":"Html Body"},"plain_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Plain Text"},"sender_name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Sender Name"},"sender_email":{"anyOf":[{"type":"string","format":"email"},{"type":"null"}],"title":"Sender Email"},"reply_to":{"anyOf":[{"type":"string","format":"email"},{"type":"null"}],"title":"Reply To"}},"type":"object","required":["subject","html_body"],"title":"IssueCreateRequest"},"IssueDetail":{"properties":{"id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Id"},"newsletter_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Newsletter Id"},"subject":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subject"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"},"sent_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sent At"}},"additionalProperties":true,"type":"object","title":"IssueDetail","description":"A single newsletter issue. Open dict — the internal handler returns\nthe row dict plus derived KPI/status fields."},"IssueSendRequest":{"properties":{"scheduled_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Scheduled At"}},"type":"object","title":"IssueSendRequest","description":"Enqueue or schedule an issue for sending. ``scheduled_at`` omitted\n(or null) sends immediately."},"IssueSendTestRequest":{"properties":{"test_email":{"type":"string","maxLength":255,"title":"Test Email"}},"type":"object","required":["test_email"],"title":"IssueSendTestRequest"},"IssueUpdateRequest":{"properties":{"subject":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Subject"},"preview_text":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Preview Text"},"html_body":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Html Body"},"plain_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Plain Text"},"sender_name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Sender Name"},"sender_email":{"anyOf":[{"type":"string","format":"email"},{"type":"null"}],"title":"Sender Email"},"reply_to":{"anyOf":[{"type":"string","format":"email"},{"type":"null"}],"title":"Reply To"}},"type":"object","title":"IssueUpdateRequest","description":"Partial update for a draft issue. All fields optional — only the\nones sent are changed (mirrors the internal ``exclude_unset=True``\nhandling in ``update_issue``)."},"JobChangeMatchRequest":{"properties":{"linkedin_urls":{"items":{"type":"string"},"type":"array","maxItems":1000,"minItems":1,"title":"Linkedin Urls","description":"LinkedIn profile URLs to match against the last 90 days of job-change events."}},"type":"object","required":["linkedin_urls"],"title":"JobChangeMatchRequest","description":"Look up which LinkedIn profiles changed job recently."},"JobChangeSignalsResponse":{"properties":{"signals":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Signals"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"JobChangeSignalsResponse","description":"Job-change events for this org.\n\nIdentifying fields are REDACTED unless the caller holds a Signals write\ncapability - these are real named people who moved employer, which is\nexactly the data a read-only role is not meant to export."},"JobControlRequest":{"properties":{"reason":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Reason"}},"type":"object","title":"JobControlRequest","description":"Why a job is being paused or cancelled. Recorded on the job."},"JobDetails":{"properties":{"job_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Job Id"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"company_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Name"},"linkedin_company_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Linkedin Company Id"},"job_location":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Location"},"posted_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Posted At"}},"additionalProperties":true,"type":"object","title":"JobDetails","description":"One posting, with its company, recruiter and the company's other jobs."},"JobPostCreate":{"properties":{"title":{"type":"string","maxLength":200,"title":"Title"},"role_type":{"type":"string","maxLength":40,"title":"Role Type"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"engagement_type":{"type":"string","maxLength":30,"title":"Engagement Type","default":"monthly"},"industries":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Industries"},"tools":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Tools"},"countries":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Countries"},"regions":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Regions"},"languages":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Languages"},"seniority":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Seniority"},"deal_size_band":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Deal Size Band"},"monthly_rate_usd_min":{"anyOf":[{"type":"number"},{"type":"string"},{"type":"null"}],"title":"Monthly Rate Usd Min"},"monthly_rate_usd_max":{"anyOf":[{"type":"number"},{"type":"string"},{"type":"null"}],"title":"Monthly Rate Usd Max"},"per_meeting_rate_usd":{"anyOf":[{"type":"number"},{"type":"string"},{"type":"null"}],"title":"Per Meeting Rate Usd"},"openings_count":{"type":"integer","minimum":1.0,"title":"Openings Count","default":1},"commission_plan_version_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Commission Plan Version Id"},"status":{"type":"string","title":"Status","default":"draft"}},"type":"object","required":["title","role_type"],"title":"JobPostCreate"},"JobPostUpdate":{"properties":{"title":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Title"},"role_type":{"anyOf":[{"type":"string","maxLength":40},{"type":"null"}],"title":"Role Type"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"engagement_type":{"anyOf":[{"type":"string","maxLength":30},{"type":"null"}],"title":"Engagement Type"},"industries":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Industries"},"tools":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Tools"},"countries":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Countries"},"regions":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Regions"},"languages":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Languages"},"seniority":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Seniority"},"deal_size_band":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Deal Size Band"},"monthly_rate_usd_min":{"anyOf":[{"type":"number"},{"type":"string"},{"type":"null"}],"title":"Monthly Rate Usd Min"},"monthly_rate_usd_max":{"anyOf":[{"type":"number"},{"type":"string"},{"type":"null"}],"title":"Monthly Rate Usd Max"},"per_meeting_rate_usd":{"anyOf":[{"type":"number"},{"type":"string"},{"type":"null"}],"title":"Per Meeting Rate Usd"},"openings_count":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Openings Count"},"commission_plan_version_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Commission Plan Version Id"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"}},"type":"object","title":"JobPostUpdate"},"JobSearchRequest":{"properties":{"keywords":{"items":{"type":"string"},"type":"array","minItems":1,"title":"Keywords","description":"Job-title keywords. OR semantics - any match counts."},"window_days":{"type":"integer","maximum":365.0,"minimum":1.0,"title":"Window Days","description":"How far back to look for postings.","default":30},"location_contains":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Location Contains","description":"Free-text token matched case-insensitively against the job location."},"persona_seniority":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Persona Seniority","description":"Decision-maker seniority filter."},"persona_department":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Persona Department","description":"Decision-maker department filter."},"persona_title_contains":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Persona Title Contains","description":"Decision-maker title substring filter."},"contacts_per_company":{"type":"integer","maximum":50.0,"minimum":1.0,"title":"Contacts Per Company","default":10},"exclude_aggregators":{"type":"boolean","title":"Exclude Aggregators","description":"Drop postings from job-board aggregators. On by default because an aggregator is not a company that is hiring - it is a company that lists other people's jobs. `/jobs/search/aggregators` returns exactly what this suppressed, so a caller can audit it.","default":true},"per_company_cap":{"type":"integer","maximum":10000.0,"minimum":1.0,"title":"Per Company Cap","description":"Max postings counted per company.","default":50},"parent_linkedin_company_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Parent Linkedin Company Id","description":"Scope to one parent company and its subsidiaries. Omit to search everywhere."},"limit":{"type":"integer","maximum":200.0,"minimum":1.0,"title":"Limit","description":"Page size. Capped at 200 to bound the ClickHouse cost.","default":50},"offset":{"type":"integer","minimum":0.0,"title":"Offset","default":0},"include_recruiters":{"type":"boolean","title":"Include Recruiters","description":"Run the recruiter aggregation and enrichment hop. Set false to skip two round-trips when only Companies and Decision-makers are needed.","default":true},"recruiter_limit":{"type":"integer","maximum":200.0,"minimum":1.0,"title":"Recruiter Limit","description":"Recruiter paging, INDEPENDENT of `limit`/`offset`: one recruiter can serve many companies, so the two counts diverge and a caller can page one tab without touching the other.","default":50},"recruiter_offset":{"type":"integer","minimum":0.0,"title":"Recruiter Offset","default":0}},"type":"object","required":["keywords"],"title":"JobSearchRequest","description":"One request shape for every Hiring Signals tab.\n\nThe app uses a single command for all of them deliberately - the form is\nflat, and each handler needs both the base filters and the persona half.\nSplitting them here would just add a layer the routes flatten back out."},"JobSearchResponse":{"properties":{"results":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Results"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"JobSearchResponse","description":"A page of Hiring Signals results.\n\nRows stay open dicts: each tab (jobs, companies, decision-makers,\nrecruiters, aggregators) returns a different shape assembled from\nClickHouse plus OpenSearch, and the columns move as enrichment improves."},"KBSearchRequest":{"properties":{"query":{"type":"string","title":"Query","description":"Search query"},"limit":{"type":"integer","maximum":50.0,"minimum":1.0,"title":"Limit","description":"Max results","default":10}},"type":"object","required":["query"],"title":"KBSearchRequest"},"KeywordAddedItem":{"properties":{"id":{"type":"string","title":"Id"},"keyword":{"type":"string","title":"Keyword","description":"Stored (lowercased) keyword text."},"signal_type":{"type":"string","title":"Signal Type"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"}},"type":"object","required":["id","keyword","signal_type"],"title":"KeywordAddedItem"},"KeywordCreateFromDomainRequest":{"properties":{"domain":{"type":"string","maxLength":253,"minLength":3,"title":"Domain","description":"Competitor domain to track, e.g. 'cognism.com'."},"page_limit":{"type":"integer","maximum":500.0,"minimum":1.0,"title":"Page Limit","description":"Max pages to seed from the domain.","default":200},"contact_limit":{"type":"integer","maximum":500.0,"minimum":1.0,"title":"Contact Limit","description":"Max contacts to pre-resolve.","default":200},"dry_run":{"type":"boolean","title":"Dry Run","description":"Preview only: find the on-domain pages and resolve contacts exactly as a real run would, but save nothing. The counts then say what WOULD be seeded, keyword_id stays null, and sample_pages / sample_contacts show a preview. Default false keeps the one-call create.","default":false}},"type":"object","required":["domain"],"title":"KeywordCreateFromDomainRequest"},"KeywordCreateFromDomainResponse":{"properties":{"keyword_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Keyword Id"},"keyword":{"type":"string","title":"Keyword"},"pages_seeded":{"type":"integer","title":"Pages Seeded","default":0},"contacts_seeded":{"type":"integer","title":"Contacts Seeded","default":0},"companies_seeded":{"type":"integer","title":"Companies Seeded","default":0},"off_domain_rejected":{"type":"integer","title":"Off Domain Rejected","default":0},"message":{"type":"string","title":"Message","default":""},"dry_run":{"type":"boolean","title":"Dry Run","description":"True when nothing was saved (preview).","default":false},"sample_pages":{"items":{"$ref":"#/components/schemas/IntentPageItem"},"type":"array","title":"Sample Pages","description":"Dry run only: up to 10 of the pages that would be seeded."},"sample_contacts":{"items":{"$ref":"#/components/schemas/CreateFromDomainSampleContact"},"type":"array","title":"Sample Contacts","description":"Dry run only: up to 10 of the contacts that would be pre-resolved (no emails)."}},"type":"object","required":["keyword"],"title":"KeywordCreateFromDomainResponse"},"KeywordCreateFromSearchItem":{"properties":{"keyword":{"type":"string","title":"Keyword"},"keyword_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Keyword Id"},"status":{"type":"string","title":"Status","description":"'created' | 'skipped' | 'error'"},"pages_seeded":{"type":"integer","title":"Pages Seeded","default":0},"contacts_seeded":{"type":"integer","title":"Contacts Seeded","default":0},"companies_seeded":{"type":"integer","title":"Companies Seeded","default":0},"error":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Error"}},"type":"object","required":["keyword","status"],"title":"KeywordCreateFromSearchItem"},"KeywordDetailRequest":{"properties":{"page":{"type":"integer","minimum":1.0,"title":"Page","default":1},"limit":{"type":"integer","maximum":500.0,"minimum":1.0,"title":"Limit","default":100},"conditions":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Conditions","description":"Optional `[{field, operator, value}]` filter conditions."}},"type":"object","title":"KeywordDetailRequest"},"KeywordFilters":{"properties":{"audience":{"type":"string","enum":["b2b","b2c","both"],"title":"Audience","description":"`b2b`, `b2c` or `both`.","default":"both"},"exclude_page_types":{"items":{"type":"string","enum":["news","finance","forum","vendor_marketing"]},"type":"array","title":"Exclude Page Types","description":"Page types to drop from the URL set."},"min_commercial_intent_level":{"type":"integer","maximum":100.0,"minimum":0.0,"title":"Min Commercial Intent Level","description":"Drop pages scored below this commercial intent.","default":0},"max_urls_per_domain":{"type":"integer","maximum":20.0,"minimum":1.0,"title":"Max Urls Per Domain","description":"Soft cap so no single domain dominates the set.","default":5},"llm_triage":{"type":"boolean","title":"Llm Triage","description":"Run a model pass over candidate pages.","default":false},"exclude_domains":{"items":{"type":"string"},"type":"array","title":"Exclude Domains","description":"Domains to drop."}},"additionalProperties":true,"type":"object","title":"KeywordFilters","description":"The filters a keyword's URL set is shaped by.\n\nMirrors the app's `KeywordSearchFilters`, including its bounds. Keys beyond\nthe typed ones are accepted and passed through, as the app accepts them."},"KeywordFiltersUpdateRequest":{"properties":{"search_filters":{"additionalProperties":true,"type":"object","title":"Search Filters","description":"Full-replacement `search_filters` JSON. Typed fields in `intent.domain.models.keyword.KeywordSearchFilters`: audience, exclude_page_types, min_commercial_intent_level, max_urls_per_domain, llm_triage, exclude_domains. Extra keys allowed."}},"type":"object","required":["search_filters"],"title":"KeywordFiltersUpdateRequest"},"KeywordSyncConfigRequest":{"properties":{"icp_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Icp Id","description":"Score matches against this ICP."},"committee_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Committee Id","description":"Buying committee whose personas are exported."},"export_mode":{"type":"string","enum":["signals_only","icp_plus_signals","all_icp_personas"],"title":"Export Mode","description":"`signals_only` exports only the people a signal named; `icp_plus_signals` adds the ICP's personas at those companies; `all_icp_personas` exports every persona regardless of signal.","default":"icp_plus_signals"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id","description":"The list matches are pushed into."},"auto_sync_enabled":{"type":"boolean","title":"Auto Sync Enabled","description":"Push on a schedule, without anyone calling anything, rather than only on request.","default":false}},"type":"object","title":"KeywordSyncConfigRequest","description":"Wire a keyword to a list, optionally on a schedule."},"KeywordsAddRequest":{"properties":{"keywords":{"items":{"type":"string","maxLength":500},"type":"array","maxItems":50,"minItems":1,"title":"Keywords","description":"1-50 keyword phrases to add as plain compete-tracking rows. Stored lowercased. Empty / whitespace-only entries and in-request duplicates (case-insensitive, trimmed) are skipped, not saved twice."},"signal_type":{"type":"string","enum":["intent","jobs","job_changes"],"title":"Signal Type","description":"Signal source discriminator, same vocabulary as the web UI: 'intent' (default, buyer-intent tracking), 'jobs', or 'job_changes'.","default":"intent"}},"type":"object","required":["keywords"],"title":"KeywordsAddRequest"},"KeywordsAddResponse":{"properties":{"created":{"items":{"$ref":"#/components/schemas/KeywordAddedItem"},"type":"array","title":"Created","default":[]},"skipped":{"items":{"$ref":"#/components/schemas/KeywordsAddSkippedItem"},"type":"array","title":"Skipped","default":[]},"created_count":{"type":"integer","title":"Created Count","default":0},"skipped_count":{"type":"integer","title":"Skipped Count","default":0}},"type":"object","title":"KeywordsAddResponse"},"KeywordsAddSkippedItem":{"properties":{"keyword":{"type":"string","title":"Keyword"},"reason":{"type":"string","title":"Reason","description":"'empty' | 'duplicate_in_request' | 'already_exists'"}},"type":"object","required":["keyword","reason"],"title":"KeywordsAddSkippedItem"},"KeywordsCreateFromSearchRequest":{"properties":{"keywords":{"items":{"type":"string","maxLength":500},"type":"array","maxItems":10,"minItems":1,"title":"Keywords","description":"1-10 free-text keyword queries. Each is searched against the intent page index, contacts/companies are resolved, and a compete-tracking keyword row is saved. Duplicates within the request (case-insensitive, trimmed) are skipped, not re-saved."},"search_filters":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Search Filters","description":"Optional intent-search filters applied to EVERY keyword in the batch (audience, page_type, commercial_score_min, etc.). Stored verbatim on each saved keyword row so the daily resolver replays them."},"semantic_ratio":{"type":"number","maximum":1.0,"minimum":0.0,"title":"Semantic Ratio","description":"0 = text search (default, cheapest), 1 = semantic, between = hybrid.","default":0.0},"page_limit":{"type":"integer","maximum":50.0,"minimum":1.0,"title":"Page Limit","description":"Max pages to seed per keyword. Deliberately smaller than create-from-domain's 200 default since this runs once per keyword.","default":20},"contact_limit":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Contact Limit","description":"Max contacts to pre-resolve per keyword.","default":50}},"type":"object","required":["keywords"],"title":"KeywordsCreateFromSearchRequest"},"KeywordsCreateFromSearchResponse":{"properties":{"results":{"items":{"$ref":"#/components/schemas/KeywordCreateFromSearchItem"},"type":"array","title":"Results","default":[]},"created_count":{"type":"integer","title":"Created Count","default":0},"skipped_count":{"type":"integer","title":"Skipped Count","default":0},"error_count":{"type":"integer","title":"Error Count","default":0}},"type":"object","title":"KeywordsCreateFromSearchResponse"},"KeywordsListRequest":{"properties":{"keyword_contains":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Keyword Contains","description":"Case-insensitive keyword substring filter."},"page":{"type":"integer","minimum":1.0,"title":"Page","default":1},"limit":{"type":"integer","maximum":500.0,"minimum":1.0,"title":"Limit","default":100}},"type":"object","title":"KeywordsListRequest"},"KnowledgeContextRequest":{"properties":{"task":{"type":"string","maxLength":2000,"minLength":1,"title":"Task"},"entity_concept_ids":{"items":{"type":"string"},"type":"array","maxItems":20,"title":"Entity Concept Ids"},"token_budget":{"anyOf":[{"type":"integer","maximum":100000.0,"minimum":100.0},{"type":"null"}],"title":"Token Budget"}},"type":"object","required":["task"],"title":"KnowledgeContextRequest"},"LandingPageConsentConfig":{"properties":{"mode":{"type":"string","enum":["off","explicit","region"],"title":"Mode","default":"off"},"regions":{"items":{"type":"string","const":"EEA"},"type":"array","minItems":1,"title":"Regions","description":"Only used when mode is `region`."},"banner":{"type":"boolean","title":"Banner","description":"False when your own consent manager drives the gate.","default":true},"title":{"type":"string","maxLength":120,"title":"Title","default":"We use cookies"},"message":{"type":"string","maxLength":600,"title":"Message","default":"We use cookies and similar technologies to measure traffic and improve this site. You can accept or reject them."},"accept_label":{"type":"string","maxLength":40,"title":"Accept Label","default":"Accept"},"reject_label":{"type":"string","maxLength":40,"title":"Reject Label","default":"Reject"},"policy_url":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Policy Url"},"policy_label":{"type":"string","maxLength":60,"title":"Policy Label","default":"Privacy policy"},"accent":{"type":"string","maxLength":7,"title":"Accent","description":"Hex colour.","default":"#111827"},"reopener":{"type":"boolean","title":"Reopener","default":true},"reopener_label":{"type":"string","maxLength":40,"title":"Reopener Label","default":"Cookie settings"},"version":{"type":"integer","maximum":1000000.0,"minimum":1.0,"title":"Version","description":"Bump to re-prompt every visitor.","default":1}},"type":"object","title":"LandingPageConsentConfig","description":"The cookie-consent gate on a published landing page."},"LandingPagePatchRequest":{"properties":{"base_sha256":{"type":"string","pattern":"^[a-f0-9]{64}$","title":"Base Sha256"},"replacements":{"items":{"$ref":"#/components/schemas/ExactReplacementRequest"},"type":"array","maxItems":20,"minItems":1,"title":"Replacements"},"idempotency_key":{"type":"string","maxLength":128,"minLength":8,"pattern":"^[A-Za-z0-9._:-]+$","title":"Idempotency Key"},"summary":{"type":"string","maxLength":500,"title":"Summary","default":"External AI edit"}},"type":"object","required":["base_sha256","replacements","idempotency_key"],"title":"LandingPagePatchRequest","description":"Conflict-safe, idempotent landing-page patch request."},"LandingPageRewriteTextRequest":{"properties":{"instruction":{"type":"string","title":"Instruction"},"selected_element":{"$ref":"#/components/schemas/SelectedElementPayload"}},"type":"object","required":["instruction","selected_element"],"title":"LandingPageRewriteTextRequest","description":"Rewrite one element's text with AI. SPENDS CREDIT.\n\nText only - it never regenerates HTML, which is what makes it the cheap\nhalf of the pair with `/edit`."},"LandingPageSetMediaEditRequest":{"properties":{"g8_action_id":{"type":"string","maxLength":120,"minLength":1,"title":"G8 Action Id"},"kind":{"type":"string","enum":["img","video"],"title":"Kind"},"remove":{"type":"boolean","title":"Remove","default":false},"src":{"anyOf":[{"type":"string","maxLength":2048},{"type":"null"}],"title":"Src"},"alt":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Alt"},"object_fit":{"anyOf":[{"type":"string","enum":["cover","contain","fill","none","scale-down"]},{"type":"null"}],"title":"Object Fit"},"object_position":{"anyOf":[{"type":"string","maxLength":80},{"type":"null"}],"title":"Object Position"},"position":{"anyOf":[{"$ref":"#/components/schemas/MediaPosition"},{"type":"null"}]},"poster":{"anyOf":[{"type":"string","maxLength":2048},{"type":"null"}],"title":"Poster"},"muted":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Muted"},"autoplay":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Autoplay"},"loop":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Loop"},"controls":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Controls"}},"type":"object","required":["g8_action_id","kind"],"title":"LandingPageSetMediaEditRequest","description":"Deterministically change one `<img>` / `<video>`. Spends nothing.\n\n`remove` true deletes the element rather than editing it, so it is the one\ndestructive field in the body."},"LandingPageSetTextRequest":{"properties":{"element_id":{"type":"string","title":"Element Id"},"new_text":{"type":"string","title":"New Text"},"selected_element":{"anyOf":[{"$ref":"#/components/schemas/SelectedElementPayload"},{"type":"null"}]}},"type":"object","required":["element_id","new_text"],"title":"LandingPageSetTextRequest","description":"Set the visible text of one element. Deterministic, spends nothing."},"LandingPageTrackingPatchRequest":{"properties":{"mode":{"anyOf":[{"type":"string","enum":["org_default","dedicated","disabled"]},{"type":"null"}],"title":"Mode","description":"`dedicated` is reached through `/tracking/provision`, not here."},"form_id":{"anyOf":[{"type":"string","maxLength":80},{"type":"null"}],"title":"Form Id"},"chat_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Chat Enabled"},"consent":{"anyOf":[{"$ref":"#/components/schemas/LandingPageConsentConfig"},{"type":"null"}]},"conversion_goal":{"anyOf":[{"type":"string","enum":["form_submission","workspace_signup","paid_account","traffic_only"]},{"type":"null"}],"title":"Conversion Goal"}},"type":"object","title":"LandingPageTrackingPatchRequest","description":"Partial update of a page's tracking. Only the fields you send change."},"LaunchAdCampaignRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Name","description":"User-provided campaign name; auto-generated if empty","default":""},"objective":{"type":"string","title":"Objective","default":"traffic"},"daily_budget":{"type":"number","exclusiveMinimum":0.0,"title":"Daily Budget","default":50.0},"currency":{"type":"string","maxLength":3,"title":"Currency","default":"USD"},"start_date":{"type":"string","format":"date","title":"Start Date"},"end_date":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"End Date"},"ad_copy_variant_index":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Ad Copy Variant Index"},"ad_image_document_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Ad Image Document Id"},"creative_image_url":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Creative Image Url","default":""},"creative_image_url_square":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Creative Image Url Square","default":""},"creative_image_url_portrait":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Creative Image Url Portrait","default":""},"logo_image_url":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Logo Image Url","default":""},"headline":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Headline","default":""},"primary_text":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Primary Text","default":""},"cta":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Cta","default":"LEARN_MORE"},"destination_url":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Destination Url","default":""},"customer_match_mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Customer Match Mode","description":"Google Customer Match mode: observation (default) | targeting | exclusion","default":"observation"},"geo_target_country":{"anyOf":[{"type":"string","maxLength":2,"minLength":2},{"type":"null"}],"title":"Geo Target Country","description":"ISO 3166-1 alpha-2 country code for the location criterion (Google observation/exclusion modes)","default":"US"},"google_campaign_subtype":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Google Campaign Subtype","description":"Google campaign subtype: display (default) | demand_gen | search","default":"display"},"include_lookalike_audiences":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Include Lookalike Audiences","description":"Demand Gen only: attach the lookalike segment derived from the Customer Match list","default":false},"custom_segment_keywords":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Custom Segment Keywords","description":"Demand Gen only: intent keywords for a custom segment (people who search these)"},"custom_segment_urls":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Custom Segment Urls","description":"Demand Gen only: competitor/relevant URLs for a custom segment (people who browse these)"},"search_keywords":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Search Keywords","description":"Google Search only: [{text, match_type: broad|phrase|exact, negative: bool}]"},"rsa_headlines":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Rsa Headlines","description":"Google Search only: 3-15 Responsive Search Ad headlines (≤30 chars each)"},"rsa_descriptions":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Rsa Descriptions","description":"Google Search only: 2-4 Responsive Search Ad descriptions (≤90 chars each)"},"video_asset_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Video Asset Ids","description":"Google Video only: 1-5 ids of the org's ad_video_assets rows to advertise"},"video_headlines":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Video Headlines","description":"Google Video only: 3-5 headlines (≤40 chars each)"},"video_long_headlines":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Video Long Headlines","description":"Google Video only: 3-5 long headlines (≤90 chars each)"},"video_descriptions":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Video Descriptions","description":"Google Video only: 3-5 descriptions (≤90 chars each)"},"video_business_name":{"anyOf":[{"type":"string","maxLength":25},{"type":"null"}],"title":"Video Business Name","description":"Google Video only: advertiser/brand name shown on the ad (≤25 chars)","default":""},"video_cta":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Video Cta","description":"Google Video only: CallToActionType enum value (e.g. LEARN_MORE, SIGN_UP)","default":"LEARN_MORE"},"selected_channels":{"anyOf":[{"additionalProperties":{"type":"boolean"},"type":"object"},{"type":"null"}],"title":"Selected Channels","description":"Google Video only: placement switches — youtube_in_stream | youtube_in_feed | youtube_shorts | discover | gmail | display | maps (true/false)"},"auto_pause_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Auto Pause At","description":"Absolute UTC instant to auto-pause at (ISO-8601 with offset)"},"auto_pause_tz":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Auto Pause Tz","description":"IANA zone the user picked in (display/intent only)"},"spend_cap":{"anyOf":[{"type":"number","exclusiveMinimum":0.0},{"type":"null"}],"title":"Spend Cap","description":"Auto-pause once lifetime SERVED spend reaches this (account currency)"},"special_ad_categories":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Special Ad Categories","description":"Meta special ad categories: HOUSING | EMPLOYMENT | CREDIT | FINANCIAL_PRODUCTS_SERVICES | ISSUES_ELECTIONS_POLITICS | ONLINE_GAMBLING_AND_GAMING | NONE"}},"type":"object","title":"LaunchAdCampaignRequest"},"LayoutSelectionRequest":{"properties":{"archetype_ids":{"items":{"type":"string"},"type":"array","title":"Archetype Ids","description":"The complete set of selected layout archetype ids."}},"type":"object","required":["archetype_ids"],"title":"LayoutSelectionRequest","description":"Mirrors `campaign_builder.routers.brand_kit.LayoutSelectionRequest`.\n\nREPLACES the org's selection. Ids come from `GET /brand-kit/archetypes`."},"LeadContentBatchRequest":{"properties":{"lead_ids":{"items":{"type":"integer"},"type":"array","maxItems":100,"minItems":1,"title":"Lead Ids"},"instructions":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Instructions"},"agent_name":{"type":"string","title":"Agent Name","default":"default-agent"},"studio_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Studio Campaign Id"}},"type":"object","required":["lead_ids"],"title":"LeadContentBatchRequest"},"LeadContentPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"LeadContentPayload","description":"Generated content, a batch's progress, or a removal count."},"LeadContentRequest":{"properties":{"instructions":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Instructions","description":"Custom instructions. Omit to derive them from the lead."},"agent_name":{"type":"string","title":"Agent Name","description":"The writing agent to use.","default":"default-agent"},"studio_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Studio Campaign Id","description":"A campaign to draw extra context from."},"contact_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Contact Id","description":"Write for this contact instead; the lead id in the path is then ignored."}},"type":"object","title":"LeadContentRequest"},"LeadCreateRequest":{"properties":{"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"type":"string","title":"Last Name"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"company":{"type":"string","title":"Company"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"Salesforce `Lead.Status` API name. Read the valid values from `GET /integrations/crm-sync/leads/statuses` - it is an OPEN picklist, so an invented value silently becomes a real status."},"lead_source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Lead Source"},"industry":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Industry"},"website":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Website"},"employee_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Employee Count"},"annual_revenue":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Annual Revenue"},"address":{"anyOf":[{"$ref":"#/components/schemas/CrmAddress"},{"type":"null"}]},"user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Id"},"custom_fields":{"items":{"$ref":"#/components/schemas/CrmCustomField"},"type":"array","title":"Custom Fields"}},"type":"object","required":["last_name","company"],"title":"LeadCreateRequest","description":"A Salesforce Lead. `last_name` and `company` are REQUIRED by Salesforce\nitself, which is why they are required here and not merely validated."},"LeadPreviewRequest":{"properties":{"connection_id":{"type":"string","title":"Connection Id","description":"Which CRM connection to preview against."},"source_mode":{"anyOf":[{"type":"string","enum":["all_qualified","saved_segment","segments_union","all_contacts"]},{"type":"null"}],"title":"Source Mode","description":"Which population to preview. `saved_segment` REQUIRES `audience_id`; `segments_union` REQUIRES `audience_ids`."},"audience_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Audience Id"},"audience_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Audience Ids"},"status_qualified":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status Qualified"},"status_unqualified":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status Unqualified"},"large_population_confirmed":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Large Population Confirmed","description":"Acknowledge that this job covers a population large enough that the app asks first. Leave unset to keep that refusal in place; set true ONLY when you have read the preview's record count and accept it. This is a safety interlock, not a tuning option - the records land in the customer's Salesforce and cannot be un-pushed."},"page_size":{"anyOf":[{"type":"integer","maximum":10000.0,"minimum":100.0},{"type":"null"}],"title":"Page Size","description":"Rows scanned per page while previewing. Omit for the app's default."}},"type":"object","required":["connection_id"],"title":"LeadPreviewRequest","description":"Queue a readiness preview of what a lead push WOULD do.\n\nNothing is written to the CRM. This is the call to make before\n`/integrations/crm-sync/leads/push`, and the only way to learn the record\ncount that `large_population_confirmed` is acknowledging."},"LeadPreviewResponse":{"properties":{},"additionalProperties":true,"type":"object","title":"LeadPreviewResponse","description":"What a lead push would do. Open-shaped - the readiness detail is\nper-provider and grows with it."},"LeadQualificationSettingsUpdateRequest":{"properties":{"qualification_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Qualification Enabled","description":"Master switch for turning visitor events into qualified leads."},"event_groups":{"anyOf":[{"additionalProperties":{"additionalProperties":{"type":"boolean"},"type":"object"},"type":"object"},{"type":"null"}],"title":"Event Groups","description":"Signal group -> event name -> enabled."},"custom_page_patterns":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Custom Page Patterns","description":"Extra URL patterns that count as a high-intent page view."},"page_patterns":{"anyOf":[{"additionalProperties":{"items":{"type":"string"},"type":"array"},"type":"object"},{"type":"null"}],"title":"Page Patterns","description":"Signal group -> URL patterns."}},"type":"object","title":"LeadQualificationSettingsUpdateRequest","description":"Mirrors `UpdateLeadQualificationSettingsRequest`. Partial update."},"LeadRemoveRequest":{"properties":{"lead_ids":{"items":{"type":"integer"},"type":"array","minItems":1,"title":"Lead Ids","description":"Leads to remove from their lists."}},"type":"object","required":["lead_ids"],"title":"LeadRemoveRequest"},"LeadStatusesResponse":{"properties":{"statuses":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Statuses"},"default":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Default","description":"The status Salesforce marks as the org default, when one exists."}},"additionalProperties":true,"type":"object","title":"LeadStatusesResponse","description":"The org's Salesforce `Lead.Status` picklist.\n\nOpen-shaped: each entry carries whatever Salesforce reports about the\nstatus, and the set of flags grows with their API. Converted statuses are\nalready filtered out by the app - setting one through the push would\nsilently convert leads."},"LeadUpdateRequest":{"properties":{"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"company":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"lead_source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Lead Source"},"industry":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Industry"},"website":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Website"},"employee_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Employee Count"},"annual_revenue":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Annual Revenue"},"address":{"anyOf":[{"$ref":"#/components/schemas/CrmAddress"},{"type":"null"}]},"user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Id"},"custom_fields":{"anyOf":[{"items":{"$ref":"#/components/schemas/CrmCustomField"},"type":"array"},{"type":"null"}],"title":"Custom Fields"}},"type":"object","title":"LeadUpdateRequest"},"LeaderboardConfigRequest":{"properties":{"id":{"type":"string","title":"Id","description":"Caller-chosen id. Reusing one upserts, matching the app."},"name":{"type":"string","title":"Name"},"roles":{"items":{"type":"string"},"type":"array","title":"Roles","description":"Which team roles appear on this board."},"kpis":{"items":{"$ref":"#/components/schemas/LeaderboardKpi"},"type":"array","title":"Kpis"},"goal":{"anyOf":[{"$ref":"#/components/schemas/LeaderboardGoal"},{"type":"null"}]},"is_system":{"type":"boolean","title":"Is System","description":"Marks a board the product ships rather than one a customer made. Accepted because the app's model has it; leave it False for your own boards.","default":false}},"type":"object","required":["id","name","roles","kpis"],"title":"LeaderboardConfigRequest","description":"A leaderboard: who is on it, what it measures, and what it is aiming at.\n\n`id` is REQUIRED and client-supplied, matching the app - these are\nconfig rows keyed by a slug the caller chooses, not server-generated\nrecords. Sending an existing id through `POST` is how the app upserts."},"LeaderboardGoal":{"properties":{"metric":{"type":"string","title":"Metric"},"target":{"type":"number","title":"Target"},"period":{"type":"string","title":"Period"}},"type":"object","required":["metric","target","period"],"title":"LeaderboardGoal","description":"The target a leaderboard is measured against."},"LeaderboardKpi":{"properties":{"id":{"type":"string","title":"Id","description":"KPI id from `GET /sales-coach/team/kpi-catalog`."},"weight":{"type":"number","title":"Weight","description":"How much this KPI counts toward the ranking."},"visible":{"type":"boolean","title":"Visible","default":true}},"type":"object","required":["id","weight"],"title":"LeaderboardKpi","description":"One metric on a leaderboard, with its weight and visibility."},"LibraryDocumentCreateRequest":{"properties":{"folder_path":{"type":"string","title":"Folder Path","description":"Where it lands, e.g. `Library/Case Studies`. The folder must already exist."},"file_name":{"type":"string","title":"File Name","description":"Stored file name."},"display_name":{"type":"string","title":"Display Name","description":"How the document is listed."},"content":{"type":"string","title":"Content","description":"The document text. Stored verbatim."},"source":{"type":"string","title":"Source","description":"Where the text came from; `manual` or `copilot` are what the app writes. NOT validated by the app, so any value is accepted and stored as given.","default":"manual"},"copilot_session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Copilot Session Id","description":"The Copilot session that produced it, when `source` is `copilot`."},"context_type":{"type":"string","enum":["global","campaign","account"],"title":"Context Type","description":"Whose library this belongs to.","default":"global"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id","description":"REQUIRED when `context_type` is `campaign`."},"account_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Id","description":"REQUIRED when `context_type` is `account`."}},"type":"object","required":["folder_path","file_name","display_name","content"],"title":"LibraryDocumentCreateRequest","description":"Create a TEXT document in the Library.\n\nMirrors `campaign_builder.routers.library.CreateDocumentRequest`. For a\nfile, use `POST /library/documents/upload` instead - this path stores the\n`content` string verbatim and runs no extraction."},"LibraryDocumentUpdateRequest":{"properties":{"display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display Name"},"content":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Content","description":"Replaces the whole document body when given."},"folder_path":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Folder Path","description":"Moves the document to another folder when given."},"meta_data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Meta Data","description":"Free-form metadata. REPLACES the stored object rather than merging."}},"type":"object","title":"LibraryDocumentUpdateRequest","description":"Edit a Library document.\n\nMirrors `library.UpdateDocumentRequest`. Every field is optional and an\nomitted field is LEFT ALONE - this is a partial update despite the PUT\nverb, which is the app's own shape."},"LibraryFolderCreateRequest":{"properties":{"name":{"type":"string","title":"Name","description":"Folder name, not a path."},"parent_path":{"type":"string","title":"Parent Path","description":"Where it hangs. `Library` is the root.","default":"Library"},"context_type":{"type":"string","enum":["global","campaign","account"],"title":"Context Type","default":"global"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id","description":"REQUIRED when `context_type` is `campaign`."},"account_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Id","description":"REQUIRED when `context_type` is `account`."}},"type":"object","required":["name"],"title":"LibraryFolderCreateRequest","description":"Create a Library folder. Mirrors `library.CreateFolderRequest`."},"LibraryFolderRenameRequest":{"properties":{"name":{"type":"string","title":"Name","description":"The new name. Documents inside keep their ids."}},"type":"object","required":["name"],"title":"LibraryFolderRenameRequest","description":"Rename a Library folder. Mirrors `library.RenameFolderRequest`."},"LifecycleAccountsExportBody":{"properties":{"columns":{"items":{"$ref":"#/components/schemas/LifecycleAccountsExportColumn"},"type":"array","maxItems":200,"minItems":1,"title":"Columns"},"lifecycle_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Lifecycle Id","description":"Lifecycle stage the grid is scoped to."},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"Status filter, e.g. `trial,trial_expired`."},"search":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Search","description":"Grid search box text."},"in_pipeline":{"type":"boolean","title":"In Pipeline","default":false},"pipeline_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Pipeline Id","description":"Open-deal scope to one pipeline (implies in_pipeline)."},"canonical_trial_cohort":{"type":"boolean","title":"Canonical Trial Cohort","default":false},"agFilterModel":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Agfiltermodel"},"agSortModel":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Agsortmodel"},"segmentFilter":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Segmentfilter"},"tz":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Tz"}},"type":"object","required":["columns"],"title":"LifecycleAccountsExportBody","description":"The lifecycle Companies grid's view to export: columns, stage, filters, search and sort."},"LifecycleAccountsExportColumn":{"properties":{"field":{"type":"string","maxLength":64,"minLength":1,"title":"Field","description":"Row field, e.g. `name` or `mrr_cents`."},"header":{"type":"string","maxLength":200,"title":"Header","description":"Column header as shown in the grid."}},"type":"object","required":["field","header"],"title":"LifecycleAccountsExportColumn","description":"One displayed grid column: the row field and the header the user sees."},"LifecycleContactsExportBody":{"properties":{"columns":{"items":{"$ref":"#/components/schemas/LifecycleContactsExportColumn"},"type":"array","maxItems":200,"minItems":1,"title":"Columns"},"lifecycle_id":{"type":"string","title":"Lifecycle Id","description":"Lifecycle stage the grid is scoped to."},"company_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Status"},"search":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Search"},"agFilterModel":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Agfiltermodel"},"agSortModel":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Agsortmodel"}},"type":"object","required":["columns","lifecycle_id"],"title":"LifecycleContactsExportBody","description":"The stage Contacts grid's view to export: columns, stage, filters, search and sort."},"LifecycleContactsExportColumn":{"properties":{"field":{"type":"string","maxLength":64,"minLength":1,"title":"Field","description":"Row field, e.g. `email` or `company_name`."},"header":{"type":"string","maxLength":200,"title":"Header","description":"Column header as shown in the grid."}},"type":"object","required":["field","header"],"title":"LifecycleContactsExportColumn","description":"One displayed grid column: the row field and the header the user sees."},"LifecycleContactsUnlockRequest":{"properties":{"lifecycle_id":{"type":"string","title":"Lifecycle Id","description":"The lifecycle stage to unlock contacts in."},"company_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Status","description":"Comma-separated company_status narrowing."},"contact_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Contact Ids","description":"Unlock exactly these. Takes precedence over `agFilterModel`."},"agFilterModel":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Agfiltermodel","description":"Grid filter model. With no `contact_ids`, every matching contact in the stage is unlocked; with neither, the WHOLE stage is."}},"type":"object","required":["lifecycle_id"],"title":"LifecycleContactsUnlockRequest"},"LifecycleEntryRequest":{"properties":{"id":{"type":"string","title":"Id"},"name":{"type":"string","maxLength":64,"minLength":1,"title":"Name"},"slug":{"type":"string","maxLength":64,"minLength":1,"title":"Slug"},"status_match":{"items":{"type":"string"},"type":"array","title":"Status Match"},"custom_status_match":{"items":{"type":"string"},"type":"array","title":"Custom Status Match"},"subscription_filter":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Subscription Filter"},"icon":{"type":"string","title":"Icon","default":"Target"},"sort_order":{"type":"integer","title":"Sort Order","default":0},"hidden":{"type":"boolean","title":"Hidden","default":false},"auto_hide_if_empty":{"type":"boolean","title":"Auto Hide If Empty","default":true},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"is_system_seed":{"type":"boolean","title":"Is System Seed","default":false},"event_tracking":{"anyOf":[{"$ref":"#/components/schemas/LifecycleEventTrackingRequest"},{"type":"null"}]},"churn_reason_categories":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Churn Reason Categories"}},"type":"object","required":["id","name","slug"],"title":"LifecycleEntryRequest","description":"One Revenue lifecycle stage.\n\n`id` is REQUIRED and may be the empty string: the app assigns a fresh UUID\nto any entry that arrives without one, which is how a new stage is created.\nMirrored as required-but-emptyable rather than optional so the field cannot\nbe omitted by accident on an entry that was meant to be an UPDATE - a\nmissing id there does not fail, it silently creates a duplicate stage and\norphans the original's documents."},"LifecycleEventConfigRequest":{"properties":{"event_name":{"type":"string","maxLength":80,"minLength":1,"title":"Event Name"},"display_name":{"type":"string","maxLength":80,"minLength":1,"title":"Display Name"},"description":{"anyOf":[{"type":"string","maxLength":240},{"type":"null"}],"title":"Description"},"bucket":{"type":"string","title":"Bucket","description":"activation | usage | expansion | risk | aha_moment"},"weight":{"anyOf":[{"type":"number","maximum":100.0,"minimum":0.0},{"type":"null"}],"title":"Weight","default":1.0},"path_to_paid_step":{"anyOf":[{"type":"integer","maximum":50.0,"minimum":0.0},{"type":"null"}],"title":"Path To Paid Step"}},"type":"object","required":["event_name","display_name","bucket"],"title":"LifecycleEventConfigRequest","description":"One tracked platform event configured against a lifecycle stage."},"LifecycleEventTrackingRequest":{"properties":{"enabled":{"type":"boolean","title":"Enabled","default":false},"events":{"items":{"$ref":"#/components/schemas/LifecycleEventConfigRequest"},"type":"array","title":"Events"}},"type":"object","title":"LifecycleEventTrackingRequest"},"LifecycleLeadStatusesPayload":{"properties":{"values":{"items":{"type":"string"},"type":"array","title":"Values","description":"Status names, e.g. `Open - Not Contacted`."}},"type":"object","title":"LifecycleLeadStatusesPayload","description":"The CRM lead statuses present on the organisation's contacts."},"LifecycleRecordItem":{"properties":{"company_id":{"type":"integer","title":"Company Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain"},"industry":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Industry"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"custom_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Custom Status"},"subscription_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subscription Status"},"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id"},"mrr_cents":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Mrr Cents"}},"type":"object","required":["company_id"],"title":"LifecycleRecordItem","description":"One company-level record in a lifecycle stage.\n\nMashup-first: ``company_id`` is ``mashup_companies.id`` — pass it straight\nto ``GET /companies/{company_id}`` or ``POST /companies/{company_id}/\nlifecycle-stage``. ``status``/``owner_id`` are coalesced across the\n``cb_accounts``/``cb_company_extensions`` overlays exactly like the\nin-app Companies lifecycle grid."},"LifecycleStageMoveRequest":{"properties":{"target_slug":{"type":"string","title":"Target Slug","description":"Destination lifecycle slug, e.g. 'suspects', 'leads', 'trials', 'customers', 'churned'. Case and surrounding whitespace are ignored, and a stage's display name is accepted too."},"dry_run":{"type":"boolean","title":"Dry Run","description":"Run every check the move runs (record exists, stage known, Customers/Churned guards, the no-subscription confirmation) and return the would-be transition without writing anything.","default":false},"confirm_without_subscription":{"type":"boolean","title":"Confirm Without Subscription","description":"Confirm a move to Customers of a company with no subscription (or a contact with no company or whose company has none). Without it such a move is refused with 409 and detail.code 'customers_without_subscription'.","default":false}},"type":"object","required":["target_slug"],"title":"LifecycleStageMoveRequest"},"LifecycleStageMoveResponse":{"properties":{"target_slug":{"type":"string","title":"Target Slug"},"previous_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Previous Status"},"new_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"New Status"},"previous_custom_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Previous Custom Status"},"new_custom_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"New Custom Status"},"dry_run":{"type":"boolean","title":"Dry Run","description":"True when this was a dry run: nothing was written.","default":false}},"type":"object","required":["target_slug"],"title":"LifecycleStageMoveResponse","description":"Mirrors the exact dict shape ``set_company_lifecycle_stage`` /\n``set_contact_lifecycle_stage`` return. Contact moves only ever populate\n``custom_status`` (contacts have no company-level ``status`` column), so\n``previous_status``/``new_status`` are null on that path."},"LifecycleStageResponse":{"properties":{"id":{"type":"string","title":"Id","description":"Lifecycle entry UUID — the key `GET /lifecycle-stages/counts` uses."},"slug":{"type":"string","title":"Slug","description":"Stable machine slug, e.g. 'leads', 'trials'. Accepted by the /records path."},"name":{"type":"string","title":"Name"},"icon":{"type":"string","title":"Icon"},"sort_order":{"type":"integer","title":"Sort Order"},"hidden":{"type":"boolean","title":"Hidden"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"status_match":{"items":{"type":"string"},"type":"array","title":"Status Match","description":"cb_accounts.status values that match this stage."},"custom_status_match":{"items":{"type":"string"},"type":"array","title":"Custom Status Match","description":"cb_accounts.custom_status values that also match this stage."},"subscription_filter":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Subscription Filter","description":"When set, cb_accounts.subscription_status must also be one of these."}},"type":"object","required":["id","slug","name","icon","sort_order","hidden"],"title":"LifecycleStageResponse","description":"One configured lifecycle entry (Suspects/Leads/Trial/Customers/Churned,\nor a custom org-defined stage)."},"LineItemCreateRequest":{"properties":{"kind":{"type":"string","enum":["commission","bonus","expense","discount"],"title":"Kind","description":"Only `discount` may carry a negative unit amount."},"label":{"type":"string","maxLength":500,"minLength":1,"title":"Label"},"quantity":{"anyOf":[{"type":"number","exclusiveMinimum":0.0},{"type":"string"}],"title":"Quantity","default":"1"},"unit_amount_usd":{"anyOf":[{"type":"number"},{"type":"string"}],"title":"Unit Amount Usd","description":"Signed. Negative is refused unless `kind` is `discount`."},"source_ref":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Source Ref"}},"additionalProperties":false,"type":"object","required":["kind","label","unit_amount_usd"],"title":"LineItemCreateRequest","description":"One money line on a statement.\n\n`extra=\"forbid\"` mirrors the app model: a typo'd field is a 422 naming it\nrather than a silently dropped charge."},"LinkLandingPageRequest":{"properties":{"landing_page_id":{"type":"string","title":"Landing Page Id"}},"type":"object","required":["landing_page_id"],"title":"LinkLandingPageRequest","description":"Attach an existing landing page to a campaign. Spends nothing."},"LinkSequenceRequest":{"properties":{"sequence_id":{"type":"string","title":"Sequence Id","description":"From `GET /inbox/emails/{email_id}/sequence-candidates`. Only sequences that actually emailed this contact are accepted."},"contact_id":{"type":"integer","title":"Contact Id","description":"Integer contact id - the CDP primary key, not an email address."}},"type":"object","required":["sequence_id","contact_id"],"title":"LinkSequenceRequest","description":"Attach an email thread to the sequence that produced it.\n\nAlso tells the sequencer the contact replied, which HALTS the remaining\nsteps of that sequence for them. That is the point of the call, not a side\neffect - linking a thread is how you stop chasing someone who answered."},"LinkTranscriptAccountRequest":{"properties":{"account_id":{"type":"string","title":"Account Id","description":"Account (company) to file the transcript under."}},"type":"object","required":["account_id"],"title":"LinkTranscriptAccountRequest","description":"Mirrors `meeting_transcripts.LinkAccountRequest`."},"LinkedInAccountConfigRequest":{"properties":{"ai_inbox_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Ai Inbox Enabled","description":"Whether the account's conversations appear in the inbox at all."},"auto_respond":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Auto Respond"},"auto_respond_config":{"anyOf":[{"$ref":"#/components/schemas/LinkedInAutoRespondConfig"},{"type":"null"}]},"sequence_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Id"},"linkedin_campaign_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Linkedin Campaign Id","description":"Provider-side campaign id to attribute conversations to."}},"type":"object","title":"LinkedInAccountConfigRequest","description":"Partial update of one LinkedIn account's inbox configuration.\n\nTurning `auto_respond` on with `require_human_review` false is the\ncombination that lets the AI message a real person unattended."},"LinkedInAccountPlan":{"properties":{"id":{"type":"integer","title":"Id","description":"Internal id; the sender id a sequence's LinkedIn channel binds to."},"account_id":{"type":"string","title":"Account Id","description":"The account id `/linkedin/accounts/{account_id}/schedule` takes."},"display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display Name"},"public_identifier":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Public Identifier"},"avatar_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Avatar Url"},"status":{"type":"string","title":"Status"},"account_timezone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Timezone"},"work_window":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Work Window"},"day":{"type":"string","title":"Day","description":"ISO date the usage counts belong to."},"invites_used":{"type":"integer","title":"Invites Used"},"invite_cap":{"type":"integer","title":"Invite Cap"},"invites_pending":{"type":"integer","title":"Invites Pending"},"messages_used":{"type":"integer","title":"Messages Used"},"message_cap":{"type":"integer","title":"Message Cap"},"messages_pending":{"type":"integer","title":"Messages Pending"},"cap_source":{"type":"string","title":"Cap Source","default":"live"},"plan_frozen_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Plan Frozen At"},"invite_cap_next":{"type":"integer","title":"Invite Cap Next"},"message_cap_next":{"type":"integer","title":"Message Cap Next"},"account_timezone_next":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Timezone Next"},"timezone_effective_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Timezone Effective At"},"account_tier":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Tier"},"is_paid":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Paid","description":"null is NOT false: it means the subscription has not been determined."},"product_statuses":{"anyOf":[{"additionalProperties":{"additionalProperties":{"type":"string"},"type":"object"},"type":"object"},{"type":"null"}],"title":"Product Statuses"},"invite_cap_with_note":{"type":"integer","title":"Invite Cap With Note"},"invite_cap_without_note":{"type":"integer","title":"Invite Cap Without Note"}},"type":"object","required":["id","account_id","status","day","invites_used","invite_cap","invites_pending","messages_used","message_cap","messages_pending","invite_cap_next","message_cap_next","invite_cap_with_note","invite_cap_without_note"],"title":"LinkedInAccountPlan","description":"One sender account: identity, pacing, today's usage against its caps, and the live queue."},"LinkedInAccountPlans":{"properties":{"accounts":{"items":{"$ref":"#/components/schemas/LinkedInAccountPlan"},"type":"array","title":"Accounts"},"total_count":{"type":"integer","title":"Total Count"}},"type":"object","required":["accounts","total_count"],"title":"LinkedInAccountPlans"},"LinkedInAccountSyncResult":{"properties":{"synced":{"type":"integer","title":"Synced"},"created":{"type":"integer","title":"Created"},"updated":{"type":"integer","title":"Updated"},"removed":{"type":"integer","title":"Removed","default":0},"webhook_registered":{"type":"boolean","title":"Webhook Registered","default":false}},"type":"object","required":["synced","created","updated"],"title":"LinkedInAccountSyncResult","description":"What an account sync changed."},"LinkedInApprovalPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"LinkedInApprovalPayload","description":"A pending LinkedIn approval list, a decision result or a seat's approval settings."},"LinkedInApproveRequest":{"properties":{"message_text":{"anyOf":[{"type":"string","maxLength":8000},{"type":"null"}],"title":"Message Text","description":"Edited message text; omit to send as drafted."},"note":{"anyOf":[{"type":"string","maxLength":300},{"type":"null"}],"title":"Note","description":"Edited connection note."}},"type":"object","title":"LinkedInApproveRequest"},"LinkedInAutoRespondConfig":{"properties":{"enabled":{"type":"boolean","title":"Enabled","default":false},"trigger_on_intents":{"items":{"type":"string"},"type":"array","title":"Trigger On Intents"},"exclude_intents":{"items":{"type":"string"},"type":"array","title":"Exclude Intents"},"require_human_review":{"type":"boolean","title":"Require Human Review","description":"True holds the reply as a draft instead of sending it.","default":true},"max_replies_per_conversation":{"type":"integer","title":"Max Replies Per Conversation","default":2},"min_delay_minutes":{"type":"integer","title":"Min Delay Minutes","default":5},"business_hours_only":{"type":"boolean","title":"Business Hours Only","default":true},"timezone":{"type":"string","title":"Timezone","default":"America/New_York"},"business_hours_start":{"type":"integer","title":"Business Hours Start","default":9},"business_hours_end":{"type":"integer","title":"Business Hours End","default":17}},"type":"object","title":"LinkedInAutoRespondConfig","description":"When the AI is allowed to answer on a LinkedIn account by itself."},"LinkedInChannelRemovalResponse":{"properties":{"sequence_id":{"type":"string","title":"Sequence Id","description":"Sequence that was operated on"},"dry_run":{"type":"boolean","title":"Dry Run","description":"True when nothing was written"},"provider":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Provider","description":"LinkedIn provider detected: NETRION, HEYREACH, or null when none was bound"},"channel_type_removed":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Channel Type Removed","description":"Persisted channel_type that was unbound, e.g. LINKEDIN_NETRION"},"steps_removed":{"type":"integer","title":"Steps Removed","description":"Number of LinkedIn steps deleted"},"channels_removed":{"type":"integer","title":"Channels Removed","description":"Number of LinkedIn channel bindings removed"},"removed_steps":{"items":{"$ref":"#/components/schemas/RemovedStepSummary"},"type":"array","title":"Removed Steps","description":"The steps that were (or would be) removed"},"remaining_step_count":{"type":"integer","title":"Remaining Step Count","description":"Steps left on the sequence afterwards"},"remaining_channel_count":{"type":"integer","title":"Remaining Channel Count","description":"Live channel bindings left afterwards"},"sequence_now_empty":{"type":"boolean","title":"Sequence Now Empty","description":"True when the sequence has no steps left"},"status_before":{"type":"string","title":"Status Before","description":"Sequence status before the operation"},"status_after":{"type":"string","title":"Status After","description":"Sequence status after the operation"},"auto_paused":{"type":"boolean","title":"Auto Paused","description":"True when a LIVE/WAITING sequence was paused as part of this operation"},"warnings":{"items":{"type":"string"},"type":"array","title":"Warnings","description":"Advisory notes the caller should surface to the user"}},"type":"object","required":["sequence_id","dry_run","steps_removed","channels_removed","remaining_step_count","remaining_channel_count","sequence_now_empty","status_before","status_after","auto_paused"],"title":"LinkedInChannelRemovalResponse","description":"Result of removing a sequence's LinkedIn steps and channel binding together.\n\nNothing bound is a SUCCESS with zero counts, never a 404 — that is what makes\nthe operation safe to call across a batch of sequences without inspecting each\none first, and it doubles as the cleanup path for a sequence already stuck\nwith orphaned LinkedIn steps."},"LinkedInComposeRequest":{"properties":{"linkedin_account_id":{"type":"integer","title":"Linkedin Account Id","description":"The sending account. Integer id."},"conversation_id":{"type":"string","title":"Conversation Id","description":"An existing conversation on that account."},"message":{"type":"string","title":"Message"},"save_as_draft":{"type":"boolean","title":"Save As Draft","description":"FALSE SENDS THE MESSAGE. True stores a draft.","default":false},"assigned_users":{"items":{"type":"string"},"type":"array","title":"Assigned Users"},"tag_ids":{"items":{"type":"string"},"type":"array","title":"Tag Ids"}},"type":"object","required":["linkedin_account_id","conversation_id","message"],"title":"LinkedInComposeRequest","description":"Compose a LinkedIn message: draft it, or SEND IT TO A REAL PERSON.\n\nONE DRAFT PER CONVERSATION. Saving a draft on a conversation that already\nhas one REPLACES it, and sending deletes whatever draft was there."},"LinkedInConnectionStatus":{"properties":{"connected":{"type":"boolean","title":"Connected"},"accounts_count":{"type":"integer","title":"Accounts Count","default":0},"api_key_hint":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Api Key Hint","description":"Masked prefix only; the secret is never returned."},"last_synced_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Synced At"},"accounts_need_attention":{"type":"boolean","title":"Accounts Need Attention","default":false},"webhook_registered":{"type":"boolean","title":"Webhook Registered","default":false}},"type":"object","required":["connected"],"title":"LinkedInConnectionStatus","description":"Whether the org's LinkedIn sending connection exists and is healthy. Never the credential itself."},"LinkedInConversationSearchRequest":{"properties":{"sequence_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Sequence Ids"},"linkedin_account_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Linkedin Account Ids"},"search":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Search"},"seen":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Seen","description":"False returns only unread conversations."},"tags":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Tags"},"updated_after":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated After"},"updated_before":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated Before"},"offset":{"type":"integer","minimum":0.0,"title":"Offset","default":0},"limit":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Limit","default":25},"sort_order":{"type":"string","enum":["asc","desc"],"title":"Sort Order","default":"desc"}},"type":"object","title":"LinkedInConversationSearchRequest","description":"Filter LinkedIn conversations. A POST because the filter is a body."},"LinkedInSchedule":{"properties":{"account_id":{"type":"string","title":"Account Id"},"days":{"items":{"type":"integer"},"type":"array","title":"Days"},"start_time":{"type":"string","title":"Start Time"},"end_time":{"type":"string","title":"End Time"},"timezone":{"type":"string","title":"Timezone"},"effective_from":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Effective From","description":"When this window starts governing sends. Changes are deferred to the account's next local midnight; today keeps the window it started with."}},"type":"object","required":["account_id","days","start_time","end_time","timezone"],"title":"LinkedInSchedule","description":"An account's send window."},"LinkedInScheduleRequest":{"properties":{"days":{"items":{"type":"integer"},"type":"array","minItems":1,"title":"Days","description":"ISO weekdays, 1 = Monday ... 7 = Sunday."},"start_time":{"type":"string","pattern":"^([01]\\d|2[0-3]):[0-5]\\d$","title":"Start Time","description":"HH:MM, local to `timezone`."},"end_time":{"type":"string","pattern":"^([01]\\d|2[0-3]):[0-5]\\d$","title":"End Time","description":"HH:MM, local to `timezone`. Must be after `start_time`."},"timezone":{"type":"string","minLength":1,"title":"Timezone","description":"IANA timezone, e.g. `Europe/London`."}},"type":"object","required":["days","start_time","end_time","timezone"],"title":"LinkedInScheduleRequest","description":"When an account may send: days, a daily window and its timezone."},"LinkedInScheduleState":{"properties":{"configured":{"type":"boolean","title":"Configured"},"schedule":{"anyOf":[{"$ref":"#/components/schemas/LinkedInSchedule"},{"type":"null"}]}},"type":"object","required":["configured"],"title":"LinkedInScheduleState","description":"The account's send window, or `schedule: null` when none is set (the default window applies)."},"LinkedInSeatSettingsRequest":{"properties":{"require_message_approval":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Require Message Approval"},"shared_with_team":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Shared With Team"}},"type":"object","title":"LinkedInSeatSettingsRequest","description":"A partial update: an omitted switch is left as it is."},"ListCollectionPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"ListCollectionPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape."},"ListCreateRequest":{"properties":{"title":{"type":"string","title":"Title","description":"Name of the list"},"type":{"type":"string","title":"Type","description":"List type: contacts, companies, suppressions, deals, leads","default":"contacts"},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description","description":"Optional note describing the list's purpose, readable by agents (#16641)"}},"type":"object","required":["title"],"title":"ListCreateRequest","description":"Request body for creating a new list."},"ListCreateResponse":{"properties":{"id":{"type":"integer","title":"Id"},"title":{"type":"string","title":"Title"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Type"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"total":{"type":"integer","title":"Total","default":0},"warning":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Warning","description":"Set when another list already has this name. The list was still created."},"duplicate_list_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Duplicate List Ids","description":"Ids of existing lists with the same name (case-insensitive), when any."}},"type":"object","required":["id","title"],"title":"ListCreateResponse"},"ListDownloadPayload":{"properties":{"filename":{"type":"string","title":"Filename"},"format":{"type":"string","enum":["csv","xlsx"],"title":"Format"},"media_type":{"type":"string","title":"Media Type"},"encoding":{"type":"string","enum":["utf-8","base64"],"title":"Encoding"},"content":{"type":"string","title":"Content"}},"type":"object","required":["filename","format","media_type","encoding","content"],"title":"ListDownloadPayload","description":"A list's rows as a file, inside the JSON envelope.\n\nCSV comes back as text (`encoding: \"utf-8\"`). XLSX is binary, so it comes\nback base64-encoded (`encoding: \"base64\"`); decode it to get the workbook."},"ListFolderAssignRequest":{"properties":{"folder_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Folder Id","description":"The folder. Null takes the list OUT of every folder."}},"type":"object","title":"ListFolderAssignRequest","description":"File one list into a folder."},"ListFolderBulkAssignRequest":{"properties":{"folder_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Folder Id","description":"The folder. Null takes the list OUT of every folder."},"audience_ids":{"items":{"type":"integer"},"type":"array","maxItems":500,"minItems":1,"title":"Audience Ids","description":"The lists to move, 1 to 500."}},"type":"object","required":["audience_ids"],"title":"ListFolderBulkAssignRequest","description":"File several lists into one folder."},"ListFolderCreateRequest":{"properties":{"title":{"type":"string","maxLength":120,"minLength":1,"title":"Title","description":"Folder title."},"visibility":{"anyOf":[{"type":"string","enum":["private","org"]},{"type":"null"}],"title":"Visibility","description":"Defaults to `private` when omitted."}},"type":"object","required":["title"],"title":"ListFolderCreateRequest"},"ListFolderIndexResponse":{"properties":{"folders":{"items":{"$ref":"#/components/schemas/ListFolderResponse"},"type":"array","title":"Folders"},"shared_folders":{"items":{"$ref":"#/components/schemas/ListFolderResponse"},"type":"array","title":"Shared Folders"},"assignments":{"additionalProperties":{"type":"string","format":"uuid"},"type":"object","title":"Assignments","description":"Map of list id -> folder id for every filed list."},"starred_ids":{"items":{"type":"integer"},"type":"array","title":"Starred Ids","description":"List ids the caller has starred."}},"type":"object","title":"ListFolderIndexResponse","description":"Folders the caller owns, plus org-visible folders owned by teammates.\n\n`folders` keeps its existing meaning - \"mine\". `shared_folders` is\nbrowse-only, mirroring the app so a rebuilt UI can render the same split."},"ListFolderResponse":{"properties":{"id":{"type":"string","format":"uuid","title":"Id","description":"Folder id."},"title":{"type":"string","title":"Title","description":"Display title."},"visibility":{"type":"string","title":"Visibility","description":"`private` (owner only) or `org` (browse-only for teammates)."},"list_count":{"type":"integer","title":"List Count","description":"Number of lists currently filed in this folder."},"is_owner":{"type":"boolean","title":"Is Owner","description":"True when the calling key's org owns the folder."},"created_by":{"type":"string","title":"Created By","description":"User id that created the folder."},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["id","title","visibility","list_count","is_owner","created_by"],"title":"ListFolderResponse","description":"A folder a developer can group lists into."},"ListFolderUpdateRequest":{"properties":{"title":{"anyOf":[{"type":"string","maxLength":120,"minLength":1},{"type":"null"}],"title":"Title"},"visibility":{"anyOf":[{"type":"string","enum":["private","org"]},{"type":"null"}],"title":"Visibility"}},"type":"object","title":"ListFolderUpdateRequest","description":"Either field may be changed independently; omit a field to leave it."},"ListPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"ListPayload","description":"An open envelope for a list, a capability map or a job result.\n\nOpen because several of these return the whole `Audience`, whose shape\ncarries per-source metadata that differs between an uploaded file, a\ndynamic query and a master list - and grows with them."},"ListPerformanceItem":{"properties":{"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"}},"additionalProperties":true,"type":"object","title":"ListPerformanceItem","description":"Per-list engagement counters. Fields mirror the app's own item."},"ListPerformanceResponse":{"properties":{"items":{"items":{"$ref":"#/components/schemas/ListPerformanceItem"},"type":"array","title":"Items"}},"type":"object","title":"ListPerformanceResponse"},"ListPipelineStep":{"properties":{"id":{"type":"string","maxLength":64,"minLength":1,"title":"Id"},"name":{"type":"string","maxLength":255,"title":"Name","default":""},"type":{"type":"string","enum":["ai","waterfall"],"title":"Type"},"config_ref":{"type":"string","maxLength":255,"title":"Config Ref","description":"An existing config's group or column id.","default":""},"inline_config":{"anyOf":[{"oneOf":[{"$ref":"#/components/schemas/InlineAIConfig"},{"$ref":"#/components/schemas/InlineQualificationConfig"},{"$ref":"#/components/schemas/InlineWaterfallConfig"}],"discriminator":{"propertyName":"kind","mapping":{"ai":"#/components/schemas/InlineAIConfig","qualification":"#/components/schemas/InlineQualificationConfig","waterfall":"#/components/schemas/InlineWaterfallConfig"}}},{"type":"null"}],"title":"Inline Config"},"run_condition":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Run Condition"},"skip_existing_values":{"type":"boolean","title":"Skip Existing Values","default":true},"skip_recently_enriched":{"type":"boolean","title":"Skip Recently Enriched","default":true},"enabled":{"type":"boolean","title":"Enabled","default":true},"ui_meta":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Ui Meta"}},"type":"object","required":["id","type"],"title":"ListPipelineStep","description":"One step. Exactly one of `config_ref` or `inline_config`."},"ListResponse":{"properties":{"id":{"type":"integer","title":"Id"},"title":{"type":"string","title":"Title"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Agent/human-readable note describing the list's purpose (#16641)"},"type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Type","description":"List type (contacts, companies, suppressions, deals, leads)"},"source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source","description":"Source of the list"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"total":{"type":"integer","title":"Total","default":0},"is_dynamic":{"type":"boolean","title":"Is Dynamic","default":false},"tags":{"items":{"type":"string"},"type":"array","title":"Tags"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"created_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created By"},"updated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated At","description":"Last change to the list. Equals created_at for a list never edited since creation."},"contact_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Contact Count","description":"Number of contacts in a contact list (null for other list types)"},"company_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Company Count","description":"Number of companies in a company list (null for other list types)"},"status_reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status Reason","description":"Why the list is not usable, or null when it is fine: 'import_failed' (a file import raised; status_detail carries the reason when known), 'import_not_finished' (an uploaded list still processing with no records an hour after it was created: the import never ran) or 'build_failed' (a list built another way, e.g. from Search, failed; re-run it from its source)."},"status_detail":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status Detail","description":"Human-readable explanation of status_reason."}},"type":"object","required":["id","title"],"title":"ListResponse","description":"Audience/list representation for the public API."},"ListRoutingDto":{"properties":{"enabled":{"type":"boolean","title":"Enabled","default":false},"field_name":{"type":"string","title":"Field Name","default":""},"list_mappings":{"additionalProperties":{"type":"integer"},"type":"object","title":"List Mappings"}},"type":"object","title":"ListRoutingDto","description":"Route records to different lists based on an AI output field."},"ListStarRequest":{"properties":{"starred":{"type":"boolean","title":"Starred","description":"True to star, false to unstar."}},"type":"object","required":["starred"],"title":"ListStarRequest","description":"Star or unstar a list."},"ListSync":{"properties":{"audience_list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Audience List Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Live list name."},"enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Enabled","description":"False on a SYNTHETIC candidate row - a list resolved by `?audience_list_id=` that has no saved sync yet."},"contact_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Contact Count","description":"Live count the worker will act on."}},"additionalProperties":true,"type":"object","title":"ListSync","description":"One audience list feeding a newsletter's subscribers."},"ListSyncEnableRequest":{"properties":{"audience_list_id":{"type":"integer","title":"Audience List Id","description":"Audience list to attach."},"attested_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Attested Text","description":"The exact consent wording shown to the operator, stored VERBATIM so the trail survives future copy edits. Send what your UI displayed, not a summary of it."}},"type":"object","required":["audience_list_id"],"title":"ListSyncEnableRequest"},"ListSyncListResponse":{"properties":{"list_syncs":{"items":{"$ref":"#/components/schemas/ListSync"},"type":"array","title":"List Syncs"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"ListSyncListResponse","description":"Audience lists attached to a newsletter.\n\nThe app returns a bare LIST here, not an object, so `from_internal` accepts\nboth that and the wrapped shapes rather than 500-ing if it ever changes."},"ListUpdateRequest":{"properties":{"title":{"type":"string","minLength":1,"title":"Title","description":"New name for the list"},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description","description":"New purpose note for the list (#16641). Omit to leave the current description unchanged; send an empty string to clear it."}},"type":"object","required":["title"],"title":"ListUpdateRequest","description":"Request body for updating an existing list's name and/or description."},"LocationItem":{"properties":{"kind":{"$ref":"#/components/schemas/LocationKind"},"address":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Address"},"link":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Link"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone"},"provider":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Provider"},"display_label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display Label"},"public":{"type":"boolean","title":"Public","default":true}},"type":"object","required":["kind"],"title":"LocationItem","description":"A single location option on an event type."},"LocationKind":{"type":"string","enum":["in_person_host","in_person_attendee","phone_host","phone_attendee","link","conferencing","custom"],"title":"LocationKind","description":"Rich location types for event types."},"LookupResponse":{"properties":{"found":{"type":"boolean","title":"Found"},"confidence":{"type":"number","title":"Confidence","default":0.0},"data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Data"}},"type":"object","required":["found"],"title":"LookupResponse"},"LpPlan":{"properties":{"sections":{"items":{"$ref":"#/components/schemas/PlanSection"},"type":"array","maxItems":8,"minItems":1,"title":"Sections"}},"type":"object","required":["sections"],"title":"LpPlan","description":"Full landing-page plan — 1..8 sections."},"MailboxActivateRequest":{"properties":{"mailboxes":{"items":{"$ref":"#/components/schemas/MailboxJobItem"},"type":"array","minItems":1,"title":"Mailboxes"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id","description":"Sequence id to attribute synced threads to. Applies to every mailbox listed."},"campaign_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Name"},"auto_respond":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Auto Respond","description":"Let the AI answer on these mailboxes. Omit to leave each mailbox as it is."},"last_unread_limit":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Last Unread Limit","description":"How many unread threads the first sync reaches back for."}},"type":"object","required":["mailboxes"],"title":"MailboxActivateRequest","description":"Start (or stop) syncing several mailboxes in one call.\n\nALL-OR-NOTHING on activate: the app returns 400 if ANY mailbox fails, and\nthe ones that succeeded stay activated. Read the `failed` list in the error\nbody rather than assuming nothing happened."},"MailboxAddressesRequest":{"properties":{"mailboxes":{"items":{"type":"string"},"type":"array","title":"Mailboxes","description":"Mailbox addresses. An empty list returns an empty result."}},"type":"object","required":["mailboxes"],"title":"MailboxAddressesRequest","description":"A list of mailbox addresses to look something up for."},"MailboxArchiveRequest":{"properties":{"is_archived":{"type":"boolean","title":"Is Archived","description":"True hides the mailbox from pickers and stops new use; false restores it"}},"type":"object","required":["is_archived"],"title":"MailboxArchiveRequest","description":"Archive a mailbox, or bring it back. Mirrors the app's `ArchiveMailboxRequest`."},"MailboxAssociatedSequencesResponse":{"properties":{"sequences":{"items":{"$ref":"#/components/schemas/AssociatedSequence"},"type":"array","title":"Sequences"},"has_associations":{"type":"boolean","title":"Has Associations","default":false}},"additionalProperties":true,"type":"object","title":"MailboxAssociatedSequencesResponse","description":"Sequences wired to a mailbox, at ANY status.\n\n`has_associations` is the field to branch on before archiving or\ncancelling - it is true whenever the list is non-empty, including for\ndraft and terminated sequences, which is exactly how the app gates those\nactions."},"MailboxBulkImportRequest":{"properties":{"csv_content":{"type":"string","title":"Csv Content","description":"Raw CSV. Credential columns are stored encrypted and never returned."}},"type":"object","required":["csv_content"],"title":"MailboxBulkImportRequest","description":"Import mailboxes from CSV. Credentials in the CSV are write-only."},"MailboxCapacityRequest":{"properties":{"contacts_per_month":{"type":"integer","minimum":0.0,"title":"Contacts Per Month","description":"Target contacts to reach per month."},"warmed":{"type":"boolean","title":"Warmed","description":"Mailbox warmup state. Advisory under the current platform-wide daily cap.","default":false},"domain_tld":{"type":"string","title":"Domain Tld","description":"TLD for the per-domain cost estimate.","default":".com"}},"type":"object","required":["contacts_per_month"],"title":"MailboxCapacityRequest","description":"Input for the warmup-aware mailbox capacity planner."},"MailboxCreateRequest":{"properties":{"email":{"type":"string","title":"Email","description":"The mailbox address, e.g. sales@acme.com"},"smtp_address":{"type":"string","title":"Smtp Address","description":"SMTP host, e.g. smtp.acme.com"},"smtp_username":{"type":"string","title":"Smtp Username"},"smtp_password":{"type":"string","title":"Smtp Password","description":"Write-only. Never returned by any endpoint."},"imap_address":{"type":"string","title":"Imap Address","description":"IMAP host, e.g. imap.acme.com"},"imap_username":{"type":"string","title":"Imap Username"},"imap_password":{"type":"string","title":"Imap Password","description":"Write-only. Never returned by any endpoint."},"display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display Name"},"smtp_port":{"type":"integer","title":"Smtp Port","default":465},"imap_port":{"type":"integer","title":"Imap Port","default":993},"authentication":{"type":"string","title":"Authentication","default":"plain"},"enable_starttls_auto":{"type":"boolean","title":"Enable Starttls Auto","default":true},"daily_limit":{"type":"integer","minimum":1.0,"title":"Daily Limit","description":"Max sends per day for this mailbox","default":40},"signature_html":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Signature Html"},"signature_plain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Signature Plain"},"use_html_signature":{"type":"boolean","title":"Use Html Signature","default":false}},"type":"object","required":["email","smtp_address","smtp_username","smtp_password","imap_address","imap_username","imap_password"],"title":"MailboxCreateRequest","description":"Connect an existing mailbox over IMAP/SMTP.\n\nGoogle/Microsoft mailboxes are not connectable through this endpoint: OAuth\nneeds a browser redirect that an API call cannot complete on its own. Connect\nthose in the app for now."},"MailboxDeleteResponse":{"properties":{"deleted":{"type":"boolean","title":"Deleted"},"mailbox_id":{"type":"integer","title":"Mailbox Id"}},"type":"object","required":["deleted","mailbox_id"],"title":"MailboxDeleteResponse"},"MailboxDomainListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"MailboxDomainListPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape.\n\nA named collection (``{\"plans\": [...]}``) keeps its own key AND gains\n``items``, so a caller can page every list surface the same way without\nmemorising which key each route chose."},"MailboxDomainPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"MailboxDomainPayload","description":"An open envelope for one provider/deliverability result.\n\nOpen on purpose. These payloads are provider state and advisory reads whose\ncontents grow with the product, and a dropped field reads as \"nothing to\nreport\" rather than \"we did not tell you\". Every value passes through\n``scrub_vendor_names`` on the way in."},"MailboxFleetHealthResponse":{"properties":{},"additionalProperties":true,"type":"object","title":"MailboxFleetHealthResponse","description":"Health roll-up across every mailbox in the org."},"MailboxHealthResponse":{"properties":{"mailbox_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Mailbox Id"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"Health status as the app computes it."}},"additionalProperties":true,"type":"object","title":"MailboxHealthResponse","description":"Deliverability health for a single mailbox."},"MailboxJobItem":{"properties":{"mailbox":{"type":"string","title":"Mailbox","description":"The mailbox address."},"provider":{"type":"string","enum":["google_mailbox","smtp"],"title":"Provider"},"display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display Name"}},"type":"object","required":["mailbox","provider"],"title":"MailboxJobItem","description":"One mailbox in a bulk activate/deactivate request."},"MailboxOverviewPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"MailboxOverviewPayload","description":"A mailbox overview document, as the app returns it."},"MailboxPasswordResetRequest":{"properties":{"email":{"type":"string","title":"Email","description":"Mailbox address whose password is being replaced"},"new_password":{"type":"string","title":"New Password","description":"Write-only. Never returned by any endpoint."}},"type":"object","required":["email","new_password"],"title":"MailboxPasswordResetRequest","description":"Replace a provider mailbox's password. Write-only - it is never returned."},"MailboxProfilePictureRequest":{"properties":{"mailbox_id":{"type":"integer","exclusiveMinimum":0.0,"title":"Mailbox Id","description":"Mailbox id (mailboxes.id) on this domain"},"profile_picture":{"type":"string","title":"Profile Picture","description":"Publicly reachable image URL"}},"type":"object","required":["mailbox_id","profile_picture"],"title":"MailboxProfilePictureRequest","description":"Set the avatar shown on mail this mailbox sends."},"MailboxPurchaseItem":{"properties":{"username":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Username","description":"Local-part, e.g. 'sales' for sales@domain"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email","description":"Full mailbox address, e.g. sales@acme.com"},"password":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Password","description":"Write-only. Never returned by any endpoint."},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name","description":"Required (non-empty) for a managed purchase — an empty last name is rejected upstream and stalls provisioning."}},"type":"object","title":"MailboxPurchaseItem","description":"One mailbox to create. Supply `username` for a managed purchase\n(`provider='managed'`) or a full `email` for `registrar`/`pilot`."},"MailboxPurchaseRequest":{"properties":{"mailboxes":{"items":{"$ref":"#/components/schemas/MailboxPurchaseItem"},"type":"array","maxItems":250,"title":"Mailboxes","description":"Mailboxes to create. Up to 5 per domain for a provider='managed' purchase, and up to 250 per request."},"enable_warmup":{"type":"boolean","title":"Enable Warmup","description":"Enroll each mailbox in warmup immediately after purchase","default":true},"warmup_settings":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Warmup Settings"},"provider":{"type":"string","enum":["registrar","managed","pilot"],"title":"Provider","default":"registrar"},"platform":{"anyOf":[{"type":"string","enum":["GOOGLE","MICROSOFT"]},{"type":"null"}],"title":"Platform","description":"Mailbox platform. Required when provider='managed'."},"warmup_engine":{"anyOf":[{"type":"string","enum":["instantly","smartlead","managed"]},{"type":"null"}],"title":"Warmup Engine","description":"Warmup engine. Omit to use the account default."}},"type":"object","required":["mailboxes"],"title":"MailboxPurchaseRequest","description":"Buy one or more mailboxes on an already-purchased/connected domain.\nSpends real credits — see the 402 contract on the route docstring."},"MailboxRecoveryListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"MailboxRecoveryListPayload","description":"Weekly health points or blocklist verdicts under `items`."},"MailboxRecoveryPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"MailboxRecoveryPayload","description":"The recovery overview, a decision outcome, or a removal request."},"MailboxResponse":{"properties":{"id":{"type":"integer","title":"Id"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"},"display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display Name"},"connection_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Connection Status","description":"active | paused | disconnected | expired | ..."},"provider":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Provider"},"daily_limit":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Daily Limit"},"allows_nurture":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Allows Nurture"},"warmup_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Warmup Enabled"},"is_archived":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Archived"},"created_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created By"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["id"],"title":"MailboxResponse","description":"A sending mailbox. Credentials are never returned."},"MailboxSettingsRequest":{"properties":{"auto_respond":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Auto Respond","description":"True lets the AI answer inbound mail on this mailbox. It will message real people."},"last_unread_limit":{"anyOf":[{"type":"integer","maximum":100.0,"minimum":1.0},{"type":"null"}],"title":"Last Unread Limit","description":"How many unread emails a sync round fetches."}},"type":"object","title":"MailboxSettingsRequest","description":"Partial update of one mailbox's inbox settings. Mirrors\n`ai_inbox.schemas.emails.MailboxSettingRequest`: omit a field to leave it alone."},"MailboxShareRequest":{"properties":{"shared_with_team":{"type":"boolean","title":"Shared With Team","description":"True makes the mailbox usable by every member of the org"}},"type":"object","required":["shared_with_team"],"title":"MailboxShareRequest","description":"Share a mailbox with the rest of the org, or stop sharing it."},"MailboxSummary":{"properties":{"id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Id"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"channel_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Channel Type","description":"SMTP, GMAIL or INBOXKIT."},"is_archived":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Archived"}},"additionalProperties":true,"type":"object","title":"MailboxSummary","description":"One mailbox as the inventory surfaces it."},"MailboxTestConnectionRequest":{"properties":{"smtp_address":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Smtp Address"},"smtp_port":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Smtp Port"},"smtp_username":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Smtp Username"},"smtp_password":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Smtp Password"},"imap_address":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Imap Address"},"imap_port":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Imap Port"},"imap_username":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Imap Username"},"imap_password":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Imap Password"}},"type":"object","title":"MailboxTestConnectionRequest","description":"Optionally override credentials for the test without saving them."},"MailboxToggleRequest":{"properties":{"mailboxes":{"items":{"type":"string"},"type":"array","minItems":1,"title":"Mailboxes","description":"Mailbox addresses."},"activate":{"type":"boolean","title":"Activate","description":"True starts syncing, false stops it."},"auto_respond":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Auto Respond"}},"type":"object","required":["mailboxes","activate"],"title":"MailboxToggleRequest","description":"Flip several mailboxes on or off, and optionally set auto-respond.\n\n`activate` is explicit rather than a toggle, so a retried request is\nidempotent instead of flipping the state back."},"MailboxUncancelRequest":{"properties":{"mailbox_ids":{"items":{"type":"integer"},"type":"array","maxItems":50,"minItems":1,"title":"Mailbox Ids","description":"Mailboxes to restore. Up to 50."}},"type":"object","required":["mailbox_ids"],"title":"MailboxUncancelRequest","description":"Reverse a scheduled cancellation. RESUMES BILLING on every mailbox listed."},"MailboxUpdateRequest":{"properties":{"display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display Name"},"smtp_address":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Smtp Address"},"smtp_port":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Smtp Port"},"smtp_username":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Smtp Username"},"smtp_password":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Smtp Password","description":"Write-only."},"imap_address":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Imap Address"},"imap_port":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Imap Port"},"imap_username":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Imap Username"},"imap_password":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Imap Password","description":"Write-only."},"daily_limit":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Daily Limit"},"allows_nurture":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Allows Nurture"},"signature_html":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Signature Html"},"signature_plain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Signature Plain"},"use_html_signature":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Use Html Signature"}},"type":"object","title":"MailboxUpdateRequest","description":"Partial update. Only supplied fields are changed."},"ManifestIssueResponse":{"properties":{"path":{"type":"string","title":"Path","description":"Pointer into the document, e.g. objects[0].attributes[1].type"},"code":{"type":"string","title":"Code","description":"Machine-readable cause. Stable; safe to branch on."},"message":{"type":"string","title":"Message"}},"type":"object","required":["path","code","message"],"title":"ManifestIssueResponse","description":"One validation problem, addressed to a line a builder can fix."},"ManifestRequest":{"properties":{"manifest":{"type":"string","title":"Manifest","description":"The full graph8.app.yaml document as text. Sent verbatim, including newlines. Rejected above 256 KiB by the parser."}},"type":"object","required":["manifest"],"title":"ManifestRequest","description":"A `graph8.app.yaml` document, verbatim."},"ManifestSummary":{"properties":{"version":{"type":"integer","title":"Version"},"app_slug":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"App Slug"},"app_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"App Name"},"object_slugs":{"items":{"type":"string"},"type":"array","title":"Object Slugs"},"attribute_count":{"type":"integer","title":"Attribute Count","default":0},"has_frontend":{"type":"boolean","title":"Has Frontend","default":false},"has_backend":{"type":"boolean","title":"Has Backend","default":false}},"type":"object","required":["version"],"title":"ManifestSummary","description":"What a valid manifest declares. The echo of a successful parse.\n\nDeliberately a summary and not the parsed document: a builder who wants the\ndocument already has it, and echoing it back would make this response the\nsecond place the shape is defined."},"ManualAcceptRequest":{"properties":{"evidence_type":{"type":"string","enum":["offline_signature","customer_email","verbal_authorization","payment_received"],"title":"Evidence Type","description":"How the customer accepted, outside the e-sign flow."},"evidence_note":{"type":"string","maxLength":2000,"minLength":3,"title":"Evidence Note","description":"What happened, in the accepter's own words. Stored on the audit row."}},"type":"object","required":["evidence_type","evidence_note"],"title":"ManualAcceptRequest","description":"Evidence for an acceptance that happened OUTSIDE graph8 e-sign.\n\nBoth fields are required by the app and stay required here. This is the\naudit trail for a quote accepted on a wire transfer or a paper contract,\nand an acceptance with no recorded reason is the one thing a finance\nsurface cannot afford."},"ManualDialRequest":{"properties":{"session_id":{"type":"string","title":"Session Id"},"user_id":{"type":"string","title":"User Id"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email"},"to_phone":{"type":"string","title":"To Phone"},"from_phone":{"type":"string","title":"From Phone"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"company":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company"},"timezone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Timezone","default":"America/New_York"},"contact_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contact Id"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"}},"type":"object","required":["session_id","user_id","to_phone","from_phone"],"title":"ManualDialRequest","description":"Mirrors `ManualDialRequest` minus `org_id`. CALLS `to_phone`."},"ManualProductCreateRequest":{"properties":{"name":{"type":"string","maxLength":500,"minLength":1,"title":"Name"},"description":{"anyOf":[{"type":"string","maxLength":5000},{"type":"null"}],"title":"Description"},"default_unit_amount":{"type":"integer","maximum":1000000000.0,"minimum":0.0,"title":"Default Unit Amount","description":"In cents."},"currency":{"type":"string","maxLength":3,"minLength":3,"title":"Currency","default":"USD"},"billing_frequency":{"type":"string","enum":["one_time","month","year","quarter"],"title":"Billing Frequency","default":"one_time"},"active":{"type":"boolean","title":"Active","default":true},"quotable":{"type":"boolean","title":"Quotable","default":true},"category":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Category"},"sort_order":{"type":"integer","maximum":10000.0,"minimum":0.0,"title":"Sort Order","default":0}},"type":"object","required":["name","default_unit_amount"],"title":"ManualProductCreateRequest","description":"A product in the org's own catalogue - quotable with or without Stripe."},"ManualProductUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":500,"minLength":1},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string","maxLength":5000},{"type":"null"}],"title":"Description"},"default_unit_amount":{"anyOf":[{"type":"integer","maximum":1000000000.0,"minimum":0.0},{"type":"null"}],"title":"Default Unit Amount"},"currency":{"anyOf":[{"type":"string","maxLength":3,"minLength":3},{"type":"null"}],"title":"Currency"},"billing_frequency":{"anyOf":[{"type":"string","enum":["one_time","month","year","quarter"]},{"type":"null"}],"title":"Billing Frequency"},"active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Active"},"quotable":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Quotable"},"category":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Category"},"sort_order":{"anyOf":[{"type":"integer","maximum":10000.0,"minimum":0.0},{"type":"null"}],"title":"Sort Order"}},"type":"object","title":"ManualProductUpdateRequest","description":"Partial update. Only the fields you send are changed."},"ManualTouchRequest":{"properties":{"channel":{"type":"string","const":"manual","title":"Channel","description":"Only `manual` touches can be added by hand.","default":"manual"},"touched_at":{"type":"string","format":"date-time","title":"Touched At","description":"When it happened. Not more than a day in the future."},"note":{"type":"string","maxLength":1000,"minLength":1,"title":"Note"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email","description":"The deal person it was with; omit for the primary contact. 422 `email_not_on_deal` otherwise."}},"type":"object","required":["touched_at","note"],"title":"ManualTouchRequest"},"MarkAbsentRequest":{"properties":{"host":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Host"},"attendees":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Attendees"}},"type":"object","title":"MarkAbsentRequest"},"MarkPostRequest":{"properties":{"status":{"type":"string","enum":["reviewed","dismissed"],"title":"Status"}},"type":"object","required":["status"],"title":"MarkPostRequest","description":"Triage one matched post."},"MarketingMeta":{"properties":{"org_id":{"type":"string","title":"Org Id"},"days":{"type":"integer","title":"Days"},"cached":{"type":"boolean","title":"Cached"},"stale":{"type":"boolean","title":"Stale","default":false},"cache_ttl":{"type":"integer","title":"Cache Ttl","default":60},"timestamp":{"type":"string","format":"date-time","title":"Timestamp"},"query_time_ms":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Query Time Ms"}},"type":"object","required":["org_id","days","cached","timestamp"],"title":"MarketingMeta","description":"Metadata for marketing analytics responses."},"MarketingResponse":{"properties":{"success":{"type":"boolean","title":"Success","default":true},"data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"items":{},"type":"array"}],"title":"Data"},"meta":{"$ref":"#/components/schemas/MarketingMeta"}},"type":"object","required":["data","meta"],"title":"MarketingResponse","description":"Standard marketing analytics response wrapper."},"MarketplaceConnectStatusResponse":{"properties":{"account":{"additionalProperties":true,"type":"object","title":"Account"}},"type":"object","required":["account"],"title":"MarketplaceConnectStatusResponse","description":"Stripe Connect onboarding state. Schema mirrors the marketplace\nhandler's response shape directly."},"MarketplaceHiring":{"properties":{"id":{"type":"string","title":"Id"},"org_id":{"type":"string","title":"Org Id"},"sdr_id":{"type":"string","title":"Sdr Id"},"status":{"type":"string","title":"Status"},"sdr_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sdr Name"},"sdr_role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sdr Role"},"sdr_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sdr Email"},"monthly_rate_usd":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Monthly Rate Usd"},"per_meeting_rate_usd":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Per Meeting Rate Usd"},"started_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Started At"}},"type":"object","required":["id","org_id","sdr_id","status"],"title":"MarketplaceHiring","description":"An active hiring contract (either side)."},"MarketplaceHiringsResponse":{"properties":{"hirings":{"items":{"$ref":"#/components/schemas/MarketplaceHiring"},"type":"array","title":"Hirings"},"count":{"type":"integer","title":"Count"}},"type":"object","required":["hirings","count"],"title":"MarketplaceHiringsResponse"},"MarketplaceInvoice":{"properties":{"id":{"type":"string","title":"Id"},"sdr_id":{"type":"string","title":"Sdr Id"},"org_id":{"type":"string","title":"Org Id"},"sdr_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sdr Name"},"status":{"type":"string","title":"Status"},"total_usd":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Total Usd"},"issued_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Issued At"},"due_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Due At"},"paid_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Paid At"}},"type":"object","required":["id","sdr_id","org_id","status"],"title":"MarketplaceInvoice","description":"An invoice. SDR-side: invoices I've issued. Org-side: invoices I owe."},"MarketplaceInvoicesResponse":{"properties":{"invoices":{"items":{"$ref":"#/components/schemas/MarketplaceInvoice"},"type":"array","title":"Invoices"},"count":{"type":"integer","title":"Count"}},"type":"object","required":["invoices","count"],"title":"MarketplaceInvoicesResponse"},"MarketplaceListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"MarketplaceListPayload","description":"A LIST result, so a bare list keeps its shape under `items`.\n\nSeveral marketplace reads return a BARE JSON array (`GET\n/v1/sdr/me/service-statements`, the line-item reads, the agency statement\nlist). Wrapping them keeps every published response an object, which is\nwhat lets the envelope carry pagination later without a breaking change."},"MarketplaceMeetingDetail":{"properties":{"meeting":{"additionalProperties":true,"type":"object","title":"Meeting"}},"type":"object","required":["meeting"],"title":"MarketplaceMeetingDetail"},"MarketplaceMeetingsResponse":{"properties":{"meetings":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Meetings"},"count":{"type":"integer","title":"Count"},"total":{"type":"integer","title":"Total"}},"type":"object","required":["meetings","count","total"],"title":"MarketplaceMeetingsResponse","description":"Generic envelope for meeting list / details — the underlying row shape\nis wide and varies (transcripts, attendees, recordings, etc.), so we pass\nit through as raw dicts under ``meetings`` rather than typing every field.\nMirrors the dialer + voice routers' opaque-payload pattern."},"MarketplaceOffer":{"properties":{"id":{"type":"string","title":"Id"},"org_id":{"type":"string","title":"Org Id"},"org_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Org Name"},"sdr_id":{"type":"string","title":"Sdr Id"},"status":{"type":"string","title":"Status"},"monthly_rate_usd":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Monthly Rate Usd"},"per_meeting_rate_usd":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Per Meeting Rate Usd"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"}},"type":"object","required":["id","org_id","sdr_id","status"],"title":"MarketplaceOffer","description":"A pending hire offer the SDR can accept or reject."},"MarketplaceOffersResponse":{"properties":{"offers":{"items":{"$ref":"#/components/schemas/MarketplaceOffer"},"type":"array","title":"Offers"},"count":{"type":"integer","title":"Count"}},"type":"object","required":["offers","count"],"title":"MarketplaceOffersResponse"},"MarketplacePayload":{"properties":{},"additionalProperties":true,"type":"object","title":"MarketplacePayload","description":"One record, or one action result."},"MarketplacePayoutAccountResponse":{"properties":{"account":{"additionalProperties":true,"type":"object","title":"Account"}},"type":"object","required":["account"],"title":"MarketplacePayoutAccountResponse"},"MarketplaceProfileResponse":{"properties":{"id":{"type":"string","title":"Id"},"email":{"type":"string","title":"Email"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"marketplace_role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Marketplace Role"},"country_code":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country Code"},"monthly_rate_usd":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Monthly Rate Usd"},"per_meeting_rate_usd":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Per Meeting Rate Usd"},"availability_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Availability Status"},"bio":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bio"},"is_complete":{"type":"boolean","title":"Is Complete","default":false}},"type":"object","required":["id","email"],"title":"MarketplaceProfileResponse","description":"Caller's own marketplace SDR profile (when the API key is personal)."},"MashupSyncPolicy":{"properties":{"enabled":{"type":"boolean","title":"Enabled","description":"Turning this on starts recurring reconciliation, which SPENDS enrichment credit.","default":false},"paused":{"type":"boolean","title":"Paused","default":false},"company_changes":{"type":"string","enum":["review","verified"],"title":"Company Changes","default":"review"},"schedule":{"$ref":"#/components/schemas/SyncSchedule"},"default_field":{"$ref":"#/components/schemas/FieldPolicy"},"fields":{"additionalProperties":{"$ref":"#/components/schemas/FieldPolicy"},"type":"object","maxProperties":256,"title":"Fields"},"audience_ids":{"items":{"type":"string"},"type":"array","maxItems":1000,"title":"Audience Ids"},"excluded_local_ids":{"items":{"type":"string"},"type":"array","maxItems":10000,"title":"Excluded Local Ids"},"minimum_confidence":{"type":"number","maximum":1.0,"minimum":0.0,"title":"Minimum Confidence","default":1.0},"resume_mode":{"type":"string","enum":["latest","review"],"title":"Resume Mode","default":"review"},"batch_size":{"type":"integer","maximum":1000.0,"minimum":1.0,"title":"Batch Size","default":100},"max_records_per_run":{"type":"integer","maximum":1000000.0,"minimum":1.0,"title":"Max Records Per Run","default":10000}},"additionalProperties":false,"type":"object","title":"MashupSyncPolicy","description":"How enriched source data is reconciled onto the customer's records."},"MaterializationSummary":{"properties":{"total":{"type":"integer","title":"Total","default":0},"ready":{"type":"integer","title":"Ready","default":0},"failed":{"type":"integer","title":"Failed","default":0},"skipped":{"type":"integer","title":"Skipped","description":"Tenants already materialized on this exact digest.","default":0}},"type":"object","title":"MaterializationSummary","description":"How the fan-out went, as counts. Never tenant ids -- see module docstring."},"McpConnectionStatus":{"properties":{"determined":{"type":"boolean","title":"Determined","description":"False when the facts could not be read (transient DB error) and the zero shape below is a fallback, not evidence — consumers should abstain from first-connect claims when False","default":true},"ever_connected":{"type":"boolean","title":"Ever Connected","description":"True if ANY MCP session row exists for this org (incl. revoked)"},"sessions_count":{"type":"integer","title":"Sessions Count","description":"Total session rows for this org (incl. expired/revoked)"},"first_connected_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Connected At","description":"ISO timestamp of the earliest session row"},"last_connected_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Connected At","description":"ISO timestamp of the most recent activity"},"last_client_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Client Type","description":"Client of the most recent session (e.g. Claude)"}},"type":"object","required":["ever_connected","sessions_count"],"title":"McpConnectionStatus"},"McpServerCreateRequest":{"properties":{"name":{"type":"string","maxLength":100,"minLength":1,"title":"Name"},"description":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Description"},"transport_type":{"type":"string","enum":["sse","stdio"],"title":"Transport Type","description":"`sse` for a remote server reached over HTTP, `stdio` for a local process."},"connection_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Connection Url","description":"Required when `transport_type` is `sse`."},"command":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Command","description":"Required when `transport_type` is `stdio`."},"args":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Args"},"env_vars":{"anyOf":[{"additionalProperties":{"type":"string"},"type":"object"},{"type":"null"}],"title":"Env Vars","description":"Environment for the server process. WRITE-ONLY: values set here are never echoed back by the read routes."},"enabled":{"type":"boolean","title":"Enabled","default":true}},"type":"object","required":["name","transport_type"],"title":"McpServerCreateRequest","description":"An MCP server an agent can call tools on.\n\n`org_id` is deliberately ABSENT even though voice's model requires it: it\nis pinned from the API key by the router and a body-supplied value would be\na tenancy hole."},"McpServerUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":100,"minLength":1},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Description"},"transport_type":{"anyOf":[{"type":"string","enum":["sse","stdio"]},{"type":"null"}],"title":"Transport Type"},"connection_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Connection Url"},"command":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Command"},"args":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Args"},"env_vars":{"anyOf":[{"additionalProperties":{"type":"string"},"type":"object"},{"type":"null"}],"title":"Env Vars"},"enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Enabled"}},"type":"object","title":"McpServerUpdateRequest","description":"Partial update. Every field is optional; omitted fields are untouched."},"MediaPosition":{"properties":{"desktop":{"$ref":"#/components/schemas/MediaPositionOffset"},"tablet":{"anyOf":[{"$ref":"#/components/schemas/MediaPositionOffset"},{"type":"null"}]},"mobile":{"anyOf":[{"$ref":"#/components/schemas/MediaPositionOffset"},{"type":"null"}]}},"type":"object","required":["desktop"],"title":"MediaPosition","description":"Per-breakpoint drag offsets. `desktop` is required; the rest inherit."},"MediaPositionOffset":{"properties":{"x":{"type":"integer","maximum":5000.0,"minimum":-5000.0,"title":"X","default":0},"y":{"type":"integer","maximum":5000.0,"minimum":-5000.0,"title":"Y","default":0}},"type":"object","title":"MediaPositionOffset","description":"One breakpoint's drag offset, in pixels."},"MeetingAttendee":{"properties":{"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"response_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Response Status","description":"Provider-reported RSVP: accepted, declined, tentative, needsAction"},"organizer":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Organizer","description":"True when this attendee is the meeting organizer"}},"type":"object","title":"MeetingAttendee","description":"Lightweight attendee record on a meeting."},"MeetingCreateRequest":{"properties":{"meeting_date":{"type":"string","title":"Meeting Date","description":"YYYY-MM-DD."},"meeting_type":{"type":"string","enum":["discovery","demo","follow_up","closing"],"title":"Meeting Type","default":"discovery"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"start_time":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Start Time","description":"ISO-8601 datetime."},"end_time":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"End Time","description":"ISO-8601 datetime."},"meeting_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Meeting Url"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"client_contact_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Client Contact Name"},"client_contact_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Client Contact Email"},"attendees":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Attendees"},"notes":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Notes"}},"type":"object","required":["meeting_date"],"title":"MeetingCreateRequest","description":"Log a meeting that happened outside the integrated calendar.\n\nCreated as `assigned_by='client'` in `status='scheduled'`. Meetings are a\nBILLING INPUT: the per-meeting rate bills rows that reach `status='taken'`,\nwhich is a separate client-side transition, not something this call does."},"MeetingDetail":{"properties":{"id":{"type":"string","title":"Id"},"channel":{"type":"string","title":"Channel","default":"meetings"},"subject":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subject"},"organizer_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Organizer Email"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email"},"start_time":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Start Time"},"end_time":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"End Time"},"meeting_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Meeting Url"},"attendees":{"items":{"$ref":"#/components/schemas/MeetingAttendee"},"type":"array","title":"Attendees"},"transcript_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Transcript Status"},"transcript_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Transcript Id"},"transcript_source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Transcript Source"},"transcript_link_source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Transcript Link Source"},"transcript_summary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Transcript Summary"},"transcript_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Transcript Text","description":"Full transcript body text (omitted when redacted)"},"transcript_redacted":{"type":"boolean","title":"Transcript Redacted","default":false},"key_topics":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Key Topics"},"action_items":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Action Items"},"meeting_tasks":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Meeting Tasks","description":"CRM tasks created from transcript action items"},"campaign_mentions":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Campaign Mentions"},"custom_fields":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Custom Fields"},"audience_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience Type"},"is_internal_only":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Internal Only"},"meeting_sensitivity":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Meeting Sensitivity"},"matched_account":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Matched Account"},"participant_links":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Participant Links"},"owner_team_member":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Owner Team Member"},"organizer_team_member":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Organizer Team Member"},"tags":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Tags"},"assignees":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Assignees"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["id"],"title":"MeetingDetail","description":"Full meeting record returned by the detail endpoint.\n\nBundles transcript text + structured extractions inline so a single\ncall returns everything a UI needs to render the meeting view. When\nthe caller lacks `meetings:see_transcripts` permission and is not a\nparticipant, `transcript_redacted=true` and transcript content is\nomitted (status / IDs still returned)."},"MeetingExtractionCustomField":{"properties":{"key":{"type":"string","title":"Key","description":"Stable key for the extracted field","default":""},"label":{"type":"string","title":"Label","description":"Display label shown in admin and downstream UI"},"instruction":{"type":"string","title":"Instruction","description":"Instruction describing what to extract","default":""},"field_type":{"type":"string","enum":["text","boolean","list"],"title":"Field Type","description":"Output type expected from the extractor","default":"text"}},"type":"object","required":["label"],"title":"MeetingExtractionCustomField","description":"Org-defined field to extract from meeting transcripts."},"MeetingExtractionGlossaryTerm":{"properties":{"term":{"type":"string","title":"Term","description":"A term, acronym, or phrase the extractor should recognize"},"explanation":{"type":"string","title":"Explanation","description":"Optional explanation of what the term means or why it matters","default":""}},"type":"object","required":["term"],"title":"MeetingExtractionGlossaryTerm","description":"Vocabulary term or acronym with optional meaning/explanation."},"MeetingExtractionScopeSettings":{"properties":{"extract_fields":{"items":{"type":"string"},"type":"array","title":"Extract Fields","description":"Structured outputs that should always be extracted"},"listen_for":{"items":{"type":"string"},"type":"array","title":"Listen For","description":"Signals and topics the extractor should prioritize"},"custom_fields":{"items":{"$ref":"#/components/schemas/MeetingExtractionCustomField"},"type":"array","title":"Custom Fields","description":"Org-defined custom fields to extract"},"custom_terms":{"items":{"$ref":"#/components/schemas/MeetingExtractionGlossaryTerm"},"type":"array","title":"Custom Terms","description":"Vocabulary terms, acronyms, and product names to recognize"}},"type":"object","title":"MeetingExtractionScopeSettings","description":"Transcript extraction settings for one meeting scope."},"MeetingExtractionSettingsUpdateRequest":{"properties":{"meeting_grounding":{"$ref":"#/components/schemas/MeetingGroundingSettings","description":"Company identity the extractor grounds on: canonical name, internal domains, aliases."},"shared":{"$ref":"#/components/schemas/MeetingExtractionScopeSettings","description":"Applied to every meeting, on top of the per-scope block."},"customer":{"$ref":"#/components/schemas/MeetingExtractionScopeSettings","description":"Meetings with an existing customer."},"prospect":{"$ref":"#/components/schemas/MeetingExtractionScopeSettings","description":"Meetings with a prospect."},"internal":{"$ref":"#/components/schemas/MeetingExtractionScopeSettings","description":"Internal meetings - every attendee is on an internal domain."}},"type":"object","title":"MeetingExtractionSettingsUpdateRequest","description":"Mirrors `campaign_builder.schemas.settings.UpdateMeetingExtractionSettingsRequest`.\n\nEvery field defaults to an EMPTY block, and the app treats the request as\nthe new state for each scope it receives - so omitting a scope is not the\nsame as sending it empty. Send the whole object you read back.\n\nThe nested blocks are the app's own models; see the module docstring."},"MeetingGroundingAlias":{"properties":{"alias":{"type":"string","title":"Alias","description":"Brand, alias, or product term as it may appear in transcripts"},"canonical_name":{"type":"string","title":"Canonical Name","description":"Canonical company or product name this alias resolves to"},"explanation":{"type":"string","title":"Explanation","description":"Optional explanation of the relationship or how this alias should be interpreted","default":""}},"type":"object","required":["alias","canonical_name"],"title":"MeetingGroundingAlias","description":"Alias, brand, or product name that should resolve to a canonical entity."},"MeetingGroundingSettings":{"properties":{"canonical_company_name":{"type":"string","title":"Canonical Company Name","description":"Canonical internal company name that should be used in summaries and task interpretation","default":""},"internal_domains":{"items":{"type":"string"},"type":"array","title":"Internal Domains","description":"Email domains that identify internal attendees"},"brand_aliases":{"items":{"$ref":"#/components/schemas/MeetingGroundingAlias"},"type":"array","title":"Brand Aliases","description":"Known brand, alias, or product names that resolve to canonical entities"},"participant_rules":{"items":{"type":"string"},"type":"array","title":"Participant Rules","description":"Rules that explain how participant and domain evidence should be interpreted"}},"type":"object","title":"MeetingGroundingSettings","description":"Org-level grounding facts used to interpret meeting participants and transcript wording."},"MeetingSensitivityRequest":{"properties":{"sensitivity":{"type":"string","enum":["normal","private"],"title":"Sensitivity","description":"`private` = participants only. `normal` = visible to the organisation. Required - there is no safe default."}},"type":"object","required":["sensitivity"],"title":"MeetingSensitivityRequest","description":"WHO MAY READ THE RECORDING OF THIS MEETING.\n\n`private` restricts the transcript to the meeting's participants.\n`normal` makes it visible to the organisation again - so moving a meeting\nfrom `private` back to `normal` EXPOSES a transcript that was restricted,\nand nobody who reads it in the meantime can be made to un-read it.\n\nThe app takes a bare `Dict[str, str]` here and defaults a MISSING or\nmisspelled key to `\"normal\"`. That default is the exposing direction, so\nthis contract makes the value REQUIRED and closed: a typo is a 422 naming\nboth options rather than a silent un-restrict."},"MeetingSummary":{"properties":{"id":{"type":"string","title":"Id"},"channel":{"type":"string","title":"Channel","default":"meetings"},"subject":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subject","description":"Meeting title"},"organizer_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Organizer Email"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email","description":"Calendar owner email (the user this meeting belongs to)"},"start_time":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Start Time"},"end_time":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"End Time"},"meeting_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Meeting Url"},"attendees":{"items":{"$ref":"#/components/schemas/MeetingAttendee"},"type":"array","title":"Attendees"},"transcript_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Transcript Status","description":"linked, missing, or no_transcript_expected"},"transcript_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Transcript Id"},"transcript_source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Transcript Source"},"transcript_summary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Transcript Summary","description":"Short transcript summary (preview only)"},"transcript_redacted":{"type":"boolean","title":"Transcript Redacted","description":"True when transcript content is hidden due to lack of permissions","default":false},"audience_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience Type","description":"customer, prospect, internal, or unknown"},"is_internal_only":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Internal Only"},"meeting_sensitivity":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Meeting Sensitivity"},"matched_account":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Matched Account"},"tags":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Tags"},"assignees":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Assignees"},"preview":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Preview","description":"Short conversational summary for inbox-card rendering"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["id"],"title":"MeetingSummary","description":"Card-level meeting record returned by the list endpoint.\n\nMirrors the UnifiedChannelItem meeting fields most clients need to\nrender a meeting list (cards / table rows). The transcript preview\nis included as `transcript_summary`; full body text is only returned\nby the detail endpoint to keep list payloads small."},"MeetingTaskCreateRequest":{"properties":{"title":{"type":"string","title":"Title","description":"What needs doing."},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"assignee_user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Assignee User Id","description":"The assignee's user id, from `GET /inbox/meetings/{meeting_id}/assignable-users`. Must be a meeting participant."},"due_date":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Due Date"},"priority":{"type":"integer","title":"Priority","description":"Lower is more urgent. The app's default is 2.","default":2}},"type":"object","required":["title"],"title":"MeetingTaskCreateRequest","description":"A follow-up task hung off a meeting.\n\nThe assignee must be a PARTICIPANT of the meeting; the server re-checks\nthat and does not trust a client-side filter."},"MeetingTaskUpdateRequest":{"properties":{"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"status":{"anyOf":[{"type":"string","enum":["open","in_progress","completed","done","cancelled"]},{"type":"null"}],"title":"Status"},"priority":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Priority"},"due_date":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Due Date"},"assignee_user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Assignee User Id"},"expected_updated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Expected Updated At","description":"Optimistic concurrency: the `updated_at` you read. If the task moved since, the update is refused instead of silently overwriting someone else's edit."}},"additionalProperties":false,"type":"object","title":"MeetingTaskUpdateRequest","description":"Patch a meeting task.\n\nNULLABLE FIELDS ARE THREE-STATE, and that is the whole point of PATCH here:\n\n  * field absent from the body        -> leave unchanged\n  * field present and `null`          -> clear it (unassign / drop due date)\n  * field present with a value        -> set it (reassignment is re-validated)\n\nThe proxy forwards with `exclude_unset=True` so the app's own\n`model_fields_set` check still distinguishes \"sent null\" from \"not sent\".\nDumping every field would turn every PATCH into a full overwrite that\ncleared whatever the caller did not mention."},"MeetingTranscriptLinkRequest":{"properties":{"transcript_id":{"type":"string","title":"Transcript Id","description":"Id of a transcript that already exists in this organisation."}},"type":"object","required":["transcript_id"],"title":"MeetingTranscriptLinkRequest","description":"Attach an existing transcript to a meeting."},"MeetingsBookedResult":{"properties":{"count":{"type":"integer","title":"Count","description":"Total booked meetings in the window","default":0},"days":{"type":"integer","title":"Days"},"upcoming_only":{"type":"boolean","title":"Upcoming Only","default":false},"page":{"type":"integer","title":"Page","description":"1-based page of the booked list","default":1},"has_next":{"type":"boolean","title":"Has Next","description":"Whether another page exists","default":false},"meetings":{"items":{"$ref":"#/components/schemas/BookedMeeting"},"type":"array","title":"Meetings"}},"type":"object","required":["days"],"title":"MeetingsBookedResult"},"MemberCloneRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Name for the clone. Defaults to '<Original Name> (AI Clone)'."}},"type":"object","title":"MemberCloneRequest","description":"Mirrors `team_members.CloneRequest`."},"MemberCreateRequest":{"properties":{"email":{"anyOf":[{"type":"string","format":"email"},{"type":"null"}],"title":"Email","description":"Email address."},"name":{"type":"string","maxLength":255,"minLength":1,"title":"Name","description":"Full name."},"title":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Title","description":"Job title."},"department":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Department","description":"Department."},"phone":{"anyOf":[{"type":"string","maxLength":50},{"type":"null"}],"title":"Phone","description":"Phone number."},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url","description":"LinkedIn profile URL."}},"type":"object","required":["name"],"title":"MemberCreateRequest","description":"Mirrors `team_members.TeamMemberCreateRequest`.\n\n`email` is an `EmailStr`, as the app's is. As a plain string a malformed\naddress would pass this layer and fail the app model built inside the\nproxy - a bare ValidationError, which is a 500."},"MemberDesktopEducationItem":{"properties":{"school":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"School"},"degree":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Degree"},"field":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Field"},"dates":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Dates"}},"type":"object","title":"MemberDesktopEducationItem","description":"Mirrors `team_members.DesktopEducationItem`."},"MemberDesktopExperienceItem":{"properties":{"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"company":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company"},"companyUrl":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Companyurl"},"employment_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Employment Type"},"dates":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Dates","description":"`<start> - <end>`; an end of `Present` marks the current role."},"duration":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Duration"},"location":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Location"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"}},"type":"object","title":"MemberDesktopExperienceItem","description":"Mirrors `team_members.DesktopExperienceItem`."},"MemberDesktopInterestItem":{"properties":{"name":{"type":"string","title":"Name"},"type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Type"}},"type":"object","required":["name"],"title":"MemberDesktopInterestItem","description":"Mirrors `team_members.DesktopInterestItem`."},"MemberDesktopProfileSyncRequest":{"properties":{"profile_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Profile Url"},"linkedin_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Id"},"full_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Full Name"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"headline":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Headline"},"location":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Location"},"about":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"About"},"profile_photo_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Profile Photo Url"},"banner_photo_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Banner Photo Url"},"is_open_to_work":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Open To Work"},"is_hiring":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Hiring"},"follower_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Follower Count"},"connection_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Connection Count"},"experiences_json":{"anyOf":[{"items":{"$ref":"#/components/schemas/MemberDesktopExperienceItem"},"type":"array"},{"type":"null"}],"title":"Experiences Json"},"education_json":{"anyOf":[{"items":{"$ref":"#/components/schemas/MemberDesktopEducationItem"},"type":"array"},{"type":"null"}],"title":"Education Json"},"skills_json":{"anyOf":[{"items":{"$ref":"#/components/schemas/MemberDesktopSkillItem"},"type":"array"},{"type":"null"}],"title":"Skills Json"},"recommendations_json":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Recommendations Json"},"accomplishments_json":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Accomplishments Json"},"interests_json":{"anyOf":[{"items":{"$ref":"#/components/schemas/MemberDesktopInterestItem"},"type":"array"},{"type":"null"}],"title":"Interests Json"},"captured_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Captured At"}},"type":"object","title":"MemberDesktopProfileSyncRequest","description":"Mirrors `team_members.DesktopProfileSyncRequest`, field for field."},"MemberDesktopSkillItem":{"properties":{"name":{"type":"string","title":"Name"},"endorsements":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Endorsements"}},"type":"object","required":["name"],"title":"MemberDesktopSkillItem","description":"Mirrors `team_members.DesktopSkillItem`."},"MemberJobHistoryItem":{"properties":{"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"company":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company"},"start_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Start Date"},"end_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"End Date"},"is_current":{"type":"boolean","title":"Is Current","default":false},"duration":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Duration"},"location":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Location"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"}},"type":"object","title":"MemberJobHistoryItem","description":"Mirrors `team_members.JobHistoryItem`."},"MemberLinkedInEnrichRequest":{"properties":{"linkedin_url":{"type":"string","title":"Linkedin Url","description":"LinkedIn profile URL to enrich from."},"overwrite":{"type":"boolean","title":"Overwrite","description":"Replace fields the person has already filled. Default fills empty fields only.","default":false}},"type":"object","required":["linkedin_url"],"title":"MemberLinkedInEnrichRequest","description":"Mirrors `team_members.LinkedInEnrichRequest`. SPENDS ENRICHMENT CREDIT."},"MemberNoteCreateRequest":{"properties":{"content":{"type":"string","title":"Content","description":"Note content."},"mentioned_users":{"items":{"$ref":"#/components/schemas/MemberNoteMention"},"type":"array","title":"Mentioned Users"}},"type":"object","required":["content"],"title":"MemberNoteCreateRequest","description":"Mirrors `team_members.TeamMemberNoteCreateRequest`."},"MemberNoteMention":{"properties":{"id":{"type":"string","title":"Id"},"name":{"type":"string","title":"Name"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"}},"type":"object","required":["id","name"],"title":"MemberNoteMention","description":"Mirrors `team_members.TeamMemberMentionedUserDto`."},"MemberNoteUpdateRequest":{"properties":{"content":{"type":"string","title":"Content","description":"Updated note content."},"mentioned_users":{"items":{"$ref":"#/components/schemas/MemberNoteMention"},"type":"array","title":"Mentioned Users"}},"type":"object","required":["content"],"title":"MemberNoteUpdateRequest","description":"Mirrors `team_members.TeamMemberNoteUpdateRequest`."},"MemberSocialImportRequest":{"properties":{"platform":{"type":"string","enum":["linkedin","twitter"],"title":"Platform","description":"Where the profile came from."},"profile_url":{"type":"string","title":"Profile Url","description":"Profile URL."},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Display name."},"headline":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Headline","description":"LinkedIn headline or Twitter bio."},"about":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"About","description":"Full bio / about section."},"current_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Current Title","description":"Current job title."},"current_company":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Current Company","description":"Current company name."},"avatar_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Avatar Url","description":"Profile picture URL."},"skills":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Skills","description":"Skills / expertise list."},"recent_posts":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Recent Posts","description":"Recent posts, used as writing samples. Each needs `text`; `scraped_at` is optional. At most three are taken per call."},"location":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Location","description":"Location."},"website":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Website","description":"Personal website URL."},"job_history":{"anyOf":[{"items":{"$ref":"#/components/schemas/MemberJobHistoryItem"},"type":"array"},{"type":"null"}],"title":"Job History","description":"Full job history. REPLACES the stored history when sent."},"username":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Username","description":"Twitter username."},"bio":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bio","description":"Twitter bio."},"followers":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Followers","description":"Follower count."},"following":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Following","description":"Following count."}},"type":"object","required":["platform","profile_url"],"title":"MemberSocialImportRequest","description":"Mirrors `team_members.SocialImportRequest`.\n\n`platform` is closed here. The app takes a free string and silently does\nNOTHING platform-specific for any value other than `linkedin` or `twitter`\n- it still commits and answers 200, so a typo would read as success."},"MemberUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":255,"minLength":1},{"type":"null"}],"title":"Name"},"title":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Title"},"department":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Department"},"phone":{"anyOf":[{"type":"string","maxLength":50},{"type":"null"}],"title":"Phone"},"avatar_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Avatar Url"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url"},"twitter_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Twitter Url"},"personal_website":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Personal Website"},"bio_short":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bio Short"},"bio_full":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bio Full"},"expertise_areas":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Expertise Areas"},"voice_tone":{"anyOf":[{"type":"string","maxLength":50},{"type":"null"}],"title":"Voice Tone"},"topics_of_interest":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Topics Of Interest"},"company":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Company"},"certifications":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Certifications"},"tools_platforms":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Tools Platforms"},"achievements":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Achievements"},"responsibilities":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Responsibilities"},"timezone":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Timezone"},"languages":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Languages"},"personal_interests":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Personal Interests"},"custom_notes":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Custom Notes"},"preferences":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Preferences","description":"Merged into the member's preferences blob, key by key."}},"type":"object","title":"MemberUpdateRequest","description":"Mirrors `team_members.TeamMemberUpdateRequest`, field for field.\n\nEvery field is optional and an omitted field is LEFT ALONE - this is a\nPATCH, not a replacement."},"MemoryCreateRequest":{"properties":{"content":{"type":"string","minLength":1,"title":"Content","description":"What to remember, in the caller's own words."},"scope":{"type":"string","title":"Scope","description":"Who the memory belongs to. `user` - only this person's Copilot recalls it. Left an open string rather than a Literal because the handler treats an unknown scope as a label rather than an error, so closing it here would refuse a call the app accepts.","default":"user"}},"type":"object","required":["content"],"title":"MemoryCreateRequest","description":"A BODY for what the app takes as query scalars. See the module docstring."},"MemoryDocumentAppendRequest":{"properties":{"subject_type":{"type":"string","title":"Subject Type","description":"What the document is about: organization, user, campaign, company or contact."},"subject_id":{"type":"string","title":"Subject Id","description":"Which one."},"content":{"type":"string","minLength":1,"title":"Content","description":"The text to append."},"file_kind":{"type":"string","title":"File Kind","description":"Which document to append to. `daily` is the rolling journal and is the default; `memory` and `soul` are the durable ones and are normally written through `PUT /copilot/memory/documents` instead.","default":"daily"}},"type":"object","required":["subject_type","subject_id","content"],"title":"MemoryDocumentAppendRequest","description":"A BODY for what the app takes as query scalars. See the module docstring."},"MemoryDocumentRequest":{"properties":{"subject_type":{"type":"string","title":"Subject Type","description":"organization | user | campaign | company | contact."},"subject_id":{"type":"string","title":"Subject Id","description":"Which one."},"file_kind":{"type":"string","title":"File Kind","description":"`soul` - who the subject is. `memory` - durable facts. `daily` - the rolling journal."},"content":{"type":"string","title":"Content","description":"The WHOLE document. This is an upsert, not an append: it replaces what is there. Use `POST /copilot/memory/documents/append` to add without replacing."},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title","description":"Display title."},"visibility":{"type":"string","title":"Visibility","description":"`shared` - the whole org's Copilot may draw on it. Defaults to shared, matching the app, so a document written without thinking about this is visible org-wide.","default":"shared"}},"type":"object","required":["subject_type","subject_id","file_kind","content"],"title":"MemoryDocumentRequest","description":"Mirror of `MemoryDocumentRequest`."},"MentionSearchRequest":{"properties":{"query":{"type":"string","title":"Query","description":"Substring to match. Empty - the default - returns the default suggestions rather than nothing, matching the app's own composer.","default":""},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id","description":"Bias results toward one campaign's people and documents."},"mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mode","description":"Which mention vocabulary to search. Left open rather than closed to a Literal: the app treats an unrecognised mode as 'no filter' instead of an error, so closing it here would turn a working call into a 422."}},"type":"object","title":"MentionSearchRequest","description":"Mirror of `MentionSearchRequest`."},"MergeDealRequest":{"properties":{"secondary_id":{"type":"string","title":"Secondary Id","description":"The deal to merge AWAY. Must be a UUID; the path deal survives."},"field_overrides":{"items":{"$ref":"#/components/schemas/DealFieldOverride"},"type":"array","title":"Field Overrides","description":"Decide individual fields yourself instead of taking the app's rules."},"trigger":{"type":"string","enum":["manual","queue","bulk_criterion"],"title":"Trigger","description":"What prompted the merge. Recorded on the audit row.","default":"manual"},"suggestion_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Suggestion Id","description":"The duplicate-suggestion this merge acts on, if any."}},"type":"object","required":["secondary_id"],"title":"MergeDealRequest","description":"Merge one deal into another. THE SECONDARY DEAL STOPS EXISTING.\n\n`secondary_id` is the deal merged AWAY; the deal in the path survives.\nPreview it first with `GET /deals/{deal_id}/merge/preview` - that call\nsays exactly which field values change and which records move."},"MergeDuplicatesRequest":{"properties":{"suggestion_ids":{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":50,"minItems":1,"title":"Suggestion Ids"},"criterion":{"type":"string","enum":["most_recent_engagement","oldest_engagement","created_first","created_last","most_recently_updated"],"title":"Criterion"}},"type":"object","required":["suggestion_ids","criterion"],"title":"MergeDuplicatesRequest","description":"Kick off a bulk merge run for up to ``BULK_MERGE_MAX_PAIRS`` suggestion\npairs. Mirrors ``duplicates/interfaces/router.py::_BulkMergeRequest``."},"MergeFieldOverride":{"properties":{"field":{"type":"string","title":"Field","description":"Field name, e.g. `CONTACT_JOB_TITLE`."},"winner":{"type":"string","enum":["primary","secondary"],"title":"Winner","description":"Which record's value to keep."}},"type":"object","required":["field","winner"],"title":"MergeFieldOverride","description":"Which side of a merge wins one field."},"MergeFilteredRequest":{"properties":{"target_list_id":{"type":"integer","title":"Target List Id","description":"List the matching records are added to."},"filter":{"items":{"$ref":"#/components/schemas/FilterCondition"},"type":"array","title":"Filter","description":"Conditions selecting the source records."},"dynamic_column_mapping":{"additionalProperties":{"type":"string"},"type":"object","title":"Dynamic Column Mapping","description":"Source-column to target-column mapping for custom columns."},"segmentFilter":{"anyOf":[{"$ref":"#/components/schemas/SegmentFilterGroup"},{"type":"null"}],"description":"Advanced AND/OR filter tree."},"conflict_resolution":{"anyOf":[{"type":"string","enum":["add_all","skip_all","custom"]},{"type":"null"}],"title":"Conflict Resolution","description":"Required when retrying after a 409. `add_all` takes every warned record, `skip_all` takes none of them, `custom` takes the ids in `include_warned_ids`. Blocked records are excluded either way."},"include_warned_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Include Warned Ids","description":"With `conflict_resolution=custom`, the warned ids to include."}},"type":"object","required":["target_list_id"],"title":"MergeFilteredRequest","description":"Add every record matching a filter into a target list.\n\nMirrors `MergeFilteredContactsRequest` / `MergeFilteredCompaniesRequest`,\nwhich are field-identical. Despite the name this MERGES A SELECTION INTO A\nLIST - it does not merge duplicate records together. `/duplicates` is the\nsurface that does that.\n\nOn a 409 the call is telling you some records need a decision; re-send\nwith `conflict_resolution` set."},"MergeRecordRequest":{"properties":{"secondary_id":{"type":"integer","title":"Secondary Id","description":"The record merged AWAY."},"field_overrides":{"items":{"$ref":"#/components/schemas/MergeFieldOverride"},"type":"array","title":"Field Overrides","description":"Decide individual fields instead of the app's rules."},"suggestion_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Suggestion Id","description":"The duplicate suggestion this merge acts on, if any."},"trigger":{"type":"string","enum":["manual","bulk_criterion"],"title":"Trigger","description":"What prompted the merge. Recorded on the audit row.","default":"manual"},"bulk_criterion":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bulk Criterion","description":"The bulk criterion, when `trigger` is `bulk_criterion`."}},"type":"object","required":["secondary_id"],"title":"MergeRecordRequest","description":"Merge `secondary_id` INTO the record in the path. The secondary stops existing.\n\nMirrors `_MergeContactRequest` / `_MergeCompanyRequest`, which are identical."},"MessageSendRequest":{"properties":{"text":{"type":"string","maxLength":20000,"minLength":1,"title":"Text"}},"type":"object","required":["text"],"title":"MessageSendRequest","description":"One message on a marketplace conversation.\n\nREACHES A PERSON: every message raises an in-app notification AND sends an\nemail to the other side."},"MigrationOwnerDecision":{"properties":{"sf_user_id":{"type":"string","maxLength":64,"minLength":1,"title":"Sf User Id","description":"The owner's Salesforce user id, as discovery listed it in `owners`."},"action":{"type":"string","enum":["invite","assign","unassigned","match"],"title":"Action","description":"`invite`: invite the owner to graph8 by email; their records are held for the invited address and become theirs when they first sign in. Invites go out in a member's name, so an API key's confirm with an `invite` decision is refused with 403. `assign`: move only their OPEN deals and OPEN tasks to the graph8 member `assign_to_team_member_id`; contacts, companies and closed records stay on the owner's placeholder. `match`: this Salesforce user IS the graph8 member `assign_to_team_member_id`; EVERY record they own moves to that member. `unassigned`: import their records with no owner."},"invite_email":{"anyOf":[{"type":"string","maxLength":320},{"type":"null"}],"title":"Invite Email","description":"`invite` only: the address to invite. Omit to use the owner's Salesforce email."},"assign_to_team_member_id":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Assign To Team Member Id","description":"`assign` and `match` only: the graph8 team member id who receives the records."}},"type":"object","required":["sf_user_id","action"],"title":"MigrationOwnerDecision","description":"What happens to the records of one Salesforce record owner who is not a graph8 member.\n\nDiscovery lists every record owner in the status's `owners`, each with a\n`match.status`. An owner whose status is `unmatched` needs a decision, or\nthe confirm is refused with 422. An owner whose status is `placeholder`\n(inactive in Salesforce, a rep who left) may only be assigned; without a\ndecision their records stay on the placeholder, as history."},"MineSignalsRequest":{"properties":{"lookback_days":{"type":"integer","maximum":365.0,"minimum":1.0,"title":"Lookback Days","default":60},"max_ideas":{"type":"integer","maximum":20.0,"minimum":1.0,"title":"Max Ideas","default":5},"sources":{"items":{"type":"string","enum":["meetings","emails"]},"type":"array","title":"Sources","description":"Which corpora to mine. Closed to the two the app accepts - it rejects anything else, and an unknown value would otherwise mine an empty corpus at full price."},"focus":{"anyOf":[{"type":"string","maxLength":300},{"type":"null"}],"title":"Focus"},"target_format":{"anyOf":[{"type":"string","enum":["landing_page","linkedin_post","newsletter_section","ad_creative"]},{"type":"null"}],"title":"Target Format"},"include_archived":{"type":"boolean","title":"Include Archived","default":true}},"type":"object","title":"MineSignalsRequest","description":"Mine conversations for content ideas. SPENDS CREDIT, per conversation.\n\nThe cost scales with `lookback_days` and the size of the corpus it\nselects - check `GET /content/calendar/ideas/corpus-stats` first, which is\nfree and tells you how many conversations each lookback tier covers.\n\n`include_archived` TRUE (the app's default) lets a previously dismissed\ntheme resurface; false is \"fresh only\"."},"MissedCallback":{"properties":{"id":{"anyOf":[{},{"type":"null"}],"title":"Id"},"caller_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Caller Phone"},"inbound_number":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Inbound Number"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"},"contact_id":{"anyOf":[{},{"type":"null"}],"title":"Contact Id"},"parallel_session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Parallel Session Id"},"created_at":{"anyOf":[{},{"type":"null"}],"title":"Created At"},"call_duration":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Call Duration"},"is_callback":{"type":"boolean","title":"Is Callback","default":false},"session":{"anyOf":[{"$ref":"#/components/schemas/MissedCallbackSession"},{"type":"null"}]},"previous_calls_count":{"type":"integer","title":"Previous Calls Count","default":0},"last_disposition":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Disposition"},"missed_reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Missed Reason"},"seen_at":{"anyOf":[{},{"type":"null"}],"title":"Seen At"},"seen_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Seen By"},"resolved_at":{"anyOf":[{},{"type":"null"}],"title":"Resolved At"},"resolved_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Resolved By"},"resolution":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Resolution"}},"type":"object","title":"MissedCallback","description":"One missed inbound callback row."},"MissedCallbackSession":{"properties":{"session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"list_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"List Title"},"list_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"List Id"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id"}},"type":"object","title":"MissedCallbackSession","description":"Parallel session the caller was previously dialed from."},"MissedCallbacksResolveRequest":{"properties":{"ids":{"items":{"type":"integer"},"type":"array","title":"Ids"},"user_email":{"type":"string","title":"User Email"},"resolution":{"type":"string","enum":["manual","ignored"],"title":"Resolution","default":"manual"}},"type":"object","required":["ids","user_email"],"title":"MissedCallbacksResolveRequest","description":"Mirrors `MissedCallResolveRequest` minus `org_id`."},"MissedCallbacksResponse":{"properties":{"missed_callbacks":{"items":{"$ref":"#/components/schemas/MissedCallback"},"type":"array","title":"Missed Callbacks"},"count":{"type":"integer","title":"Count","default":0}},"type":"object","title":"MissedCallbacksResponse"},"MissedCallbacksSeenAllRequest":{"properties":{"user_email":{"type":"string","title":"User Email"}},"type":"object","required":["user_email"],"title":"MissedCallbacksSeenAllRequest","description":"Mirrors `MissedCallSeenAllRequest`."},"MissedCallbacksSeenRequest":{"properties":{"ids":{"items":{"type":"integer"},"type":"array","title":"Ids"},"user_email":{"type":"string","title":"User Email"}},"type":"object","required":["ids","user_email"],"title":"MissedCallbacksSeenRequest","description":"Mirrors `MissedCallSeenRequest` minus `org_id`."},"MissedCallbacksUnresolveRequest":{"properties":{"ids":{"items":{"type":"integer"},"type":"array","title":"Ids"},"user_email":{"type":"string","title":"User Email"}},"type":"object","required":["ids","user_email"],"title":"MissedCallbacksUnresolveRequest","description":"Mirrors `MissedCallUnresolveRequest` minus `org_id`."},"MixAndMatchApplyRequest":{"properties":{"selections":{"items":{"$ref":"#/components/schemas/MixAndMatchSelection"},"type":"array","maxItems":100,"minItems":1,"title":"Selections"}},"type":"object","required":["selections"],"title":"MixAndMatchApplyRequest"},"MixAndMatchPreviewRequest":{"properties":{"speed":{"anyOf":[{"type":"string","enum":["relaxed","standard","fast"]},{"type":"null"}],"title":"Speed","description":"Finish within 15, 10 or 5 send-days.","default":"fast"},"target_date":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"Target Date","description":"Finish by this date; overrides `speed`."},"sender_mode":{"type":"string","enum":["keep","mix"],"title":"Sender Mode","description":"`keep` adds mailboxes of the senders already on each sequence; `mix` of the `senders` listed.","default":"keep"},"senders":{"items":{"type":"string"},"type":"array","maxItems":50,"title":"Senders","description":"Sender tags for `mix` mode; empty = any."}},"type":"object","title":"MixAndMatchPreviewRequest"},"MixAndMatchSelection":{"properties":{"sequence_id":{"type":"string","title":"Sequence Id"},"mailbox_ids":{"items":{"type":"integer"},"type":"array","maxItems":500,"minItems":1,"title":"Mailbox Ids"}},"type":"object","required":["sequence_id","mailbox_ids"],"title":"MixAndMatchSelection"},"ModifyListMembershipsRequest":{"properties":{"list_id":{"type":"string","title":"List Id","description":"The CRM's list id."},"add_contact_ids":{"items":{"type":"string"},"type":"array","title":"Add Contact Ids"},"remove_contact_ids":{"items":{"type":"string"},"type":"array","title":"Remove Contact Ids"}},"type":"object","required":["list_id"],"title":"ModifyListMembershipsRequest","description":"Add and/or remove contacts from one CRM list, in a single call.\n\nBoth lists are applied in the same request, so this is not two calls\npretending to be one - and a retry with the same body is idempotent on the\nprovider side."},"MyMailboxesResponse":{"properties":{"mailboxes":{"items":{"$ref":"#/components/schemas/MailboxSummary"},"type":"array","title":"Mailboxes"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"MyMailboxesResponse"},"NewEntry":{"properties":{"hiring_id":{"type":"string","format":"uuid","title":"Hiring Id"},"collection":{"$ref":"#/components/schemas/Collection"}},"additionalProperties":false,"type":"object","required":["hiring_id","collection"],"title":"NewEntry"},"NewPlan":{"properties":{"terms":{"$ref":"#/components/schemas/PlanTerms"},"previous_version_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Previous Version Id"}},"additionalProperties":false,"type":"object","required":["terms"],"title":"NewPlan"},"NewsletterCampaignLinkRequest":{"properties":{"campaign_id":{"type":"string","title":"Campaign Id","description":"The Studio campaign to link."}},"type":"object","required":["campaign_id"],"title":"NewsletterCampaignLinkRequest"},"NewsletterCreateRequest":{"properties":{"name":{"type":"string","maxLength":255,"title":"Name"},"goal":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Goal"}},"type":"object","required":["name"],"title":"NewsletterCreateRequest","description":"Create a new newsletter. Mirrors ``CreateNewsletterRequest``."},"NewsletterDetail":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"slug":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slug"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"goal":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Goal"},"audience_list_id":{"anyOf":[{},{"type":"null"}],"title":"Audience List Id"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"}},"additionalProperties":true,"type":"object","title":"NewsletterDetail","description":"A single newsletter row. Open dict — mirrors ``_serialize_newsletter``."},"NewsletterIssueGenerateRequest":{"properties":{"prompt":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Prompt","description":"What the issue should cover."},"html_mode":{"type":"string","enum":["email_safe","modern"],"title":"Html Mode","description":"`email_safe`: table layout, inline CSS. `modern`: div layout.","default":"email_safe"},"template_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Template Id","description":"Base the issue on this template."}},"type":"object","title":"NewsletterIssueGenerateRequest"},"NewsletterListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"NewsletterListPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape."},"NewsletterPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"NewsletterPayload","description":"An open envelope for a newsletter, an issue, a template or a send row."},"NewsletterSelectionsRequest":{"properties":{"archetype_ids":{"items":{"type":"string"},"type":"array","title":"Archetype Ids","description":"The complete set of selected newsletter archetype ids."}},"type":"object","required":["archetype_ids"],"title":"NewsletterSelectionsRequest","description":"Mirrors `campaign_builder.routers.brand_kit.NewsletterSelectionsBody`.\n\nREPLACES the org's selection. Ids come from `GET /brand-kit/newsletter-archetypes`."},"NewsletterStatusResponse":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"Status after the transition, e.g. `paused`, `completed`."}},"additionalProperties":true,"type":"object","title":"NewsletterStatusResponse","description":"The result of a lifecycle transition."},"NewsletterStudioPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"NewsletterStudioPayload","description":"An issue, version list, template, verification job or link result."},"NewsletterTemplateUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"subject":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subject"},"preview_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Preview Text"},"html_body":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Html Body"}},"type":"object","title":"NewsletterTemplateUpdateRequest"},"NextBatchRequest":{"properties":{"previous_batch_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Previous Batch Id"},"from_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"From Phone"},"from_phone_scope":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"From Phone Scope"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email"},"agent_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent Id"},"entity_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Type"},"parallel_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Parallel Count"},"dialing_mode":{"anyOf":[{"type":"string","enum":["power","parallel"]},{"type":"null"}],"title":"Dialing Mode"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id"},"campaign_builder_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Builder Campaign Id"},"order_spec":{"anyOf":[{"$ref":"#/components/schemas/OrderSpec"},{"type":"null"}]},"filter_spec":{"anyOf":[{"$ref":"#/components/schemas/FilterSpec"},{"type":"null"}]},"resume_intent":{"type":"boolean","title":"Resume Intent","default":false},"force_next_contact":{"anyOf":[{"$ref":"#/components/schemas/ForceNextContact"},{"type":"null"}]}},"type":"object","title":"NextBatchRequest","description":"Mirrors `NextBatchRequest`. THIS REQUEST DIALS PEOPLE.\n\n`parallel_count` is how many humans are called AT ONCE."},"NoteBatchRequest":{"properties":{"contact_ids":{"items":{"type":"string"},"type":"array","title":"Contact Ids","description":"Contacts whose notes to read in one call."}},"type":"object","required":["contact_ids"],"title":"NoteBatchRequest","description":"Mirrors `BatchNotesRequest`."},"NoteCreateRequest":{"properties":{"content":{"type":"string","title":"Content","description":"Note content (plain text or markdown)"}},"type":"object","required":["content"],"title":"NoteCreateRequest"},"NoteMentionedUser":{"properties":{"id":{"type":"string","title":"Id","description":"User id."},"name":{"type":"string","title":"Name","description":"Display name."},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email","description":"Email address."}},"type":"object","required":["id","name"],"title":"NoteMentionedUser","description":"Mirrors `contacts.usecases.notes.cmd.MentionedUser`."},"NoteRecordLinkRequest":{"properties":{"entity_type":{"type":"string","title":"Entity Type","description":"Record type."},"entity_id":{"type":"string","title":"Entity Id","description":"Record id."}},"type":"object","required":["entity_type","entity_id"],"title":"NoteRecordLinkRequest","description":"Mirrors `NoteRecordRequest`."},"NoteReplyCreateRequest":{"properties":{"body":{"type":"string","title":"Body","description":"Reply text."},"author_avatar_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Author Avatar Url","description":"Avatar to show beside the reply."},"mentioned_user_ids":{"items":{"type":"string"},"type":"array","title":"Mentioned User Ids","description":"Users to notify."}},"type":"object","required":["body"],"title":"NoteReplyCreateRequest","description":"Post a reply on a note's discussion thread. Internal to the org."},"NoteReplyUpdateRequest":{"properties":{"body":{"type":"string","title":"Body","description":"Replacement text."}},"type":"object","required":["body"],"title":"NoteReplyUpdateRequest","description":"Edit a note reply. Author only."},"NoteResponse":{"properties":{"id":{"type":"string","title":"Id"},"entity_type":{"type":"string","title":"Entity Type"},"entity_id":{"type":"string","title":"Entity Id"},"content":{"type":"string","title":"Content"},"created_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created By"},"created_by_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created By Name"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"},"read_only":{"type":"boolean","title":"Read Only","default":false}},"type":"object","required":["id","entity_type","entity_id","content"],"title":"NoteResponse"},"NoteUpdateRequest":{"properties":{"content":{"type":"string","title":"Content","description":"Updated note content"}},"type":"object","required":["content"],"title":"NoteUpdateRequest"},"NurtureCreateRequest":{"properties":{"name":{"type":"string","minLength":1,"title":"Name","description":"Nurture name."},"pinned_mailbox_id":{"type":"integer","title":"Pinned Mailbox Id","description":"The ONE mailbox this nurture sends from. Required: a nurture is pinned to a single sender so its consented audience always hears from the same address, and every email channel attached must use it. `validate_nurture_rules` rejects a nurture without one, so this is required here rather than left to fail deeper in."},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email","description":"Owner of the nurture. Defaults to the identity the key was minted under. A PERSONAL nurture can only be owned by the caller - supplying anyone else's address with `is_shared=false` is a 403."},"is_shared":{"type":"boolean","title":"Is Shared","description":"True makes the nurture visible org-wide. Requires an Admin or Owner role; see this router's note on org-scope promotion.","default":false},"status":{"type":"string","title":"Status","description":"Initial status. Nurtures start drafted.","default":"drafted"},"finish_on_reply":{"type":"boolean","title":"Finish On Reply","description":"Stop nurturing a contact once they reply.","default":true},"send_in_same_thread":{"type":"boolean","title":"Send In Same Thread","description":"Keep follow-ups in the original email thread.","default":true},"wait_for_new_contacts":{"type":"boolean","title":"Wait For New Contacts","default":false},"include_unsubscribe_cta":{"type":"boolean","title":"Include Unsubscribe Cta","description":"Append the visible reply-opt-out CTA to email bodies.","default":true},"associated_list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Associated List Id","description":"Audience list whose contacts this nurture engages."},"schedule_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Schedule Id"},"textual_agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Textual Agent Name"},"voice_agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Voice Agent Name"},"steps":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Steps","description":"Sequence steps, in order."},"channels":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Channels","description":"Sending channels to attach."},"campaign_builder_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Builder Campaign Id","description":"Studio campaign to link this nurture to."}},"type":"object","required":["name","pinned_mailbox_id"],"title":"NurtureCreateRequest","description":"Create a nurture.\n\n`sequence_kind` is NOT accepted: the app pins it to `nurture` server-side\nand re-validates, which is what makes the nurture-specific channel rules\nfire. A client-supplied kind would either be ignored or, worse, look\nhonoured."},"NurtureDuplicateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Name for the copy. Defaults to the source name with ' (Copy)' appended."},"is_shared":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Shared","description":"Share setting for the copy. Omit to INHERIT the source's setting - which means duplicating an already-shared nurture still needs Admin/Owner even though this field was never sent."},"is_new_list":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is New List","description":"Give the copy a fresh contacts list instead of reusing the source's."},"new_list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"New List Id","description":"Existing list for the copy. Ignored unless `is_new_list` is true."}},"type":"object","title":"NurtureDuplicateRequest","description":"Copy a nurture. The copy is always owned by the caller and starts drafted.\n\n`user_email` is deliberately absent: the app pins the copy's owner to the\ncaller regardless of what is sent, so accepting the field would advertise\ncontrol the endpoint does not grant."},"NurtureListResponse":{"properties":{"nurtures":{"items":{"$ref":"#/components/schemas/NurtureResponse"},"type":"array","title":"Nurtures"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"NurtureListResponse","description":"A page of nurtures the caller may see - their own plus org-shared."},"NurtureResponse":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"draft, live, paused, completed, terminated."},"is_shared":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Shared","description":"True when visible org-wide."},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated At"}},"additionalProperties":true,"type":"object","title":"NurtureResponse","description":"One nurture sequence."},"NurtureUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"associated_list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Associated List Id"},"textual_agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Textual Agent Name"},"voice_agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Voice Agent Name"},"is_shared":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Shared","description":"Set true to promote the nurture to org scope. Admin/Owner only - this is the one field on this model that is permission-gated."},"finish_on_reply":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Finish On Reply"},"send_in_same_thread":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Send In Same Thread"},"wait_for_new_contacts":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Wait For New Contacts"},"include_unsubscribe_cta":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Include Unsubscribe Cta"},"schedule_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Schedule Id"},"appointment_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Appointment Id"}},"type":"object","title":"NurtureUpdateRequest","description":"Patch a nurture. Every field optional; omit one to leave it unchanged."},"OIDCConfigRequest":{"properties":{"provider_name":{"type":"string","title":"Provider Name","description":"IdP name: okta, azure, google, custom."},"client_id":{"type":"string","title":"Client Id"},"client_secret":{"type":"string","title":"Client Secret","description":"Stored, never returned by the read endpoint."},"authorize_url":{"type":"string","title":"Authorize Url"},"token_url":{"type":"string","title":"Token Url"},"userinfo_url":{"type":"string","title":"Userinfo Url"},"require_sso":{"type":"boolean","title":"Require Sso","description":"See the SAML note — set this later.","default":false},"allowed_domains":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Allowed Domains"}},"type":"object","required":["provider_name","client_id","client_secret","authorize_url","token_url","userinfo_url"],"title":"OIDCConfigRequest","description":"OIDC sign-in configuration.\n\n`client_secret` is write-only in effect: the app stores it and the read\nendpoint does not hand it back."},"ObjectBoardGroup":{"properties":{"value":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Value"},"label":{"type":"string","title":"Label"},"total":{"type":"integer","title":"Total"}},"type":"object","required":["value","label","total"],"title":"ObjectBoardGroup"},"ObjectBoardPage":{"properties":{"state":{"$ref":"#/components/schemas/ObjectViewState"},"group_value":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Group Value"},"offset":{"type":"integer","maximum":1000000.0,"minimum":0.0,"title":"Offset","default":0},"limit":{"type":"integer","maximum":50.0,"minimum":1.0,"title":"Limit","default":20}},"additionalProperties":false,"type":"object","required":["state"],"title":"ObjectBoardPage"},"ObjectCreateRequest":{"properties":{"slug":{"type":"string","maxLength":100,"minLength":1,"pattern":"^[a-z][a-z0-9_]*$","title":"Slug"},"singular_noun":{"type":"string","maxLength":100,"minLength":1,"title":"Singular Noun"},"plural_noun":{"type":"string","maxLength":100,"minLength":1,"title":"Plural Noun"},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description"},"icon":{"anyOf":[{"type":"string","enum":["box","briefcase","building","calendar","flag","folder","globe","heart","layers","package","target","users"]},{"type":"null"}],"title":"Icon"}},"additionalProperties":false,"type":"object","required":["slug","singular_noun","plural_noun"],"title":"ObjectCreateRequest"},"ObjectCsvInspect":{"properties":{"csv":{"type":"string","maxLength":2000000,"minLength":1,"title":"Csv"}},"additionalProperties":false,"type":"object","required":["csv"],"title":"ObjectCsvInspect"},"ObjectCsvInspection":{"properties":{"headers":{"items":{"type":"string"},"type":"array","title":"Headers"},"sample":{"items":{"items":{"type":"string"},"type":"array"},"type":"array","title":"Sample"},"total":{"type":"integer","title":"Total"}},"type":"object","required":["headers","sample","total"],"title":"ObjectCsvInspection"},"ObjectCsvPreview":{"properties":{"schema_fingerprint":{"type":"string","title":"Schema Fingerprint"},"total":{"type":"integer","title":"Total"},"completed":{"type":"integer","title":"Completed"},"rows":{"items":{"$ref":"#/components/schemas/ImportPreviewRow"},"type":"array","title":"Rows"},"next_offset":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Next Offset"}},"type":"object","required":["schema_fingerprint","total","completed","rows","next_offset"],"title":"ObjectCsvPreview"},"ObjectCsvReceipt":{"properties":{"rows":{"items":{"$ref":"#/components/schemas/ImportReceiptRow"},"type":"array","title":"Rows"},"skipped_rows":{"items":{"$ref":"#/components/schemas/ImportSkippedRow"},"type":"array","title":"Skipped Rows"},"created":{"type":"integer","title":"Created"},"updated":{"type":"integer","title":"Updated"},"skipped":{"type":"integer","title":"Skipped"},"already_imported":{"type":"integer","title":"Already Imported"},"replayed":{"type":"boolean","title":"Replayed","default":false},"completed":{"type":"integer","title":"Completed"},"total":{"type":"integer","title":"Total"},"error_rows":{"type":"integer","title":"Error Rows"},"error_file_available":{"type":"boolean","title":"Error File Available"},"status":{"type":"string","enum":["draft","partial","completed","expired"],"title":"Status"}},"type":"object","required":["rows","created","updated","skipped","already_imported","completed","total","error_rows","error_file_available","status"],"title":"ObjectCsvReceipt","description":"Outcome of one committed page. ``created`` / ``updated`` / ``skipped`` count\nthis request only; rows an earlier attempt already imported are\n``already_imported``. ``completed`` and ``error_rows`` are the import's totals."},"ObjectDefinitionResponse":{"properties":{"slug":{"type":"string","title":"Slug","description":"Stable API slug for the object type, e.g. `invoices`."},"singular_noun":{"type":"string","title":"Singular Noun","description":"Display name for one record, e.g. \"Invoice\"."},"plural_noun":{"type":"string","title":"Plural Noun","description":"Display name for many records, e.g. \"Invoices\"."},"is_system":{"type":"boolean","title":"Is System","description":"True for objects graph8 ships; system objects cannot be deleted.","default":false},"is_archived":{"type":"boolean","title":"Is Archived","description":"Archived objects are hidden from listings.","default":false},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Customer-configured object description."},"icon":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Icon","description":"Configured graph8 icon name; null uses the default."},"display_attribute_slug":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display Attribute Slug","description":"Active single-value field used to label records; null uses the default."}},"type":"object","required":["slug","singular_noun","plural_noun"],"title":"ObjectDefinitionResponse","description":"One custom object type in the caller's workspace."},"ObjectExportRequest":{"properties":{"format":{"type":"string","enum":["csv","json"],"title":"Format","default":"csv"},"state":{"$ref":"#/components/schemas/ObjectViewState"}},"additionalProperties":false,"type":"object","title":"ObjectExportRequest"},"ObjectImportCommit":{"properties":{"revision":{"type":"integer","minimum":1.0,"title":"Revision","description":"The draft revision this page was planned against"},"offset":{"type":"integer","maximum":4999.0,"minimum":0.0,"title":"Offset","default":0},"limit":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Limit","default":100},"schema_fingerprint":{"type":"string","pattern":"^[a-f0-9]{64}$","title":"Schema Fingerprint"},"expected":{"items":{"$ref":"#/components/schemas/ImportRowExpectation"},"type":"array","maxItems":100,"minItems":1,"title":"Expected"}},"additionalProperties":false,"type":"object","required":["revision","schema_fingerprint","expected"],"title":"ObjectImportCommit"},"ObjectImportCreate":{"properties":{"mapping":{"additionalProperties":{"type":"string"},"type":"object","maxProperties":200,"title":"Mapping"},"mode":{"type":"string","enum":["create","upsert"],"title":"Mode","default":"create"},"matching_attribute":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Matching Attribute"},"filename":{"type":"string","maxLength":255,"minLength":1,"title":"Filename"},"csv":{"type":"string","maxLength":2000000,"minLength":1,"title":"Csv"}},"additionalProperties":false,"type":"object","required":["filename","csv"],"title":"ObjectImportCreate"},"ObjectImportDetail":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"owner_id":{"type":"string","title":"Owner Id"},"owner_type":{"type":"string","enum":["user","api"],"title":"Owner Type"},"filename":{"type":"string","title":"Filename"},"revision":{"type":"integer","title":"Revision"},"total":{"type":"integer","title":"Total"},"completed":{"type":"integer","title":"Completed"},"error_rows":{"type":"integer","title":"Error Rows"},"status":{"type":"string","enum":["draft","partial","completed","expired"],"title":"Status"},"source_available":{"type":"boolean","title":"Source Available"},"expires_at":{"type":"string","format":"date-time","title":"Expires At"},"created_at":{"type":"string","format":"date-time","title":"Created At"},"updated_at":{"type":"string","format":"date-time","title":"Updated At"},"setup":{"$ref":"#/components/schemas/ObjectImportSetup"},"headers":{"items":{"type":"string"},"type":"array","title":"Headers"},"sample":{"items":{"items":{"type":"string"},"type":"array"},"type":"array","title":"Sample","description":"First rows of the file while it is still stored"}},"type":"object","required":["id","owner_id","owner_type","filename","revision","total","completed","error_rows","status","source_available","expires_at","created_at","updated_at","setup","headers"],"title":"ObjectImportDetail"},"ObjectImportSetup":{"properties":{"mapping":{"additionalProperties":{"type":"string"},"type":"object","maxProperties":200,"title":"Mapping"},"mode":{"type":"string","enum":["create","upsert"],"title":"Mode","default":"create"},"matching_attribute":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Matching Attribute"}},"additionalProperties":false,"type":"object","title":"ObjectImportSetup","description":"Column mapping (CSV header -> field slug) and match mode. May be\nincomplete while saved; preview and commit need an executable setup."},"ObjectImportSummary":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"owner_id":{"type":"string","title":"Owner Id"},"owner_type":{"type":"string","enum":["user","api"],"title":"Owner Type"},"filename":{"type":"string","title":"Filename"},"revision":{"type":"integer","title":"Revision"},"total":{"type":"integer","title":"Total"},"completed":{"type":"integer","title":"Completed"},"error_rows":{"type":"integer","title":"Error Rows"},"status":{"type":"string","enum":["draft","partial","completed","expired"],"title":"Status"},"source_available":{"type":"boolean","title":"Source Available"},"expires_at":{"type":"string","format":"date-time","title":"Expires At"},"created_at":{"type":"string","format":"date-time","title":"Created At"},"updated_at":{"type":"string","format":"date-time","title":"Updated At"}},"type":"object","required":["id","owner_id","owner_type","filename","revision","total","completed","error_rows","status","source_available","expires_at","created_at","updated_at"],"title":"ObjectImportSummary","description":"History metadata: never cell values."},"ObjectImportUpdate":{"properties":{"mapping":{"additionalProperties":{"type":"string"},"type":"object","maxProperties":200,"title":"Mapping"},"mode":{"type":"string","enum":["create","upsert"],"title":"Mode","default":"create"},"matching_attribute":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Matching Attribute"},"filename":{"type":"string","maxLength":255,"minLength":1,"title":"Filename"}},"additionalProperties":false,"type":"object","required":["filename"],"title":"ObjectImportUpdate"},"ObjectRecordResponse":{"properties":{"id":{"type":"string","title":"Id","description":"Opaque record identifier."},"object_slug":{"type":"string","title":"Object Slug","description":"The object type this record belongs to."},"values":{"additionalProperties":true,"type":"object","title":"Values","description":"Currently active values, keyed by attribute slug. Shapes follow each attribute's own type; call `GET /objects/{object_slug}/attributes` for the schema."},"is_archived":{"type":"boolean","title":"Is Archived","description":"Archived records are excluded from listings.","default":false},"revision":{"type":"integer","minimum":1.0,"title":"Revision","description":"Record revision for conditional updates.","default":1},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["id","object_slug"],"title":"ObjectRecordResponse","description":"One record, with its currently active attribute values."},"ObjectSyncFieldMapping":{"properties":{"crm_field":{"type":"string","maxLength":255,"minLength":1,"title":"Crm Field"},"attribute_id":{"type":"string","format":"uuid","title":"Attribute Id"},"authority":{"anyOf":[{"type":"string","enum":["crm","graph8","newest"]},{"type":"null"}],"title":"Authority"},"restricted_acknowledged":{"type":"boolean","title":"Restricted Acknowledged","default":false},"direction":{"anyOf":[{"type":"string","enum":["pull","push","both"]},{"type":"null"}],"title":"Direction"}},"additionalProperties":false,"type":"object","required":["crm_field","attribute_id"],"title":"ObjectSyncFieldMapping","description":"A field of a sync; ``direction`` limits it to one side of a \"Both\" sync (default: the sync's)."},"ObjectSyncFieldRule":{"properties":{"crm_field":{"type":"string","maxLength":255,"minLength":1,"title":"Crm Field"},"attribute_id":{"type":"string","format":"uuid","title":"Attribute Id"},"authority":{"anyOf":[{"type":"string","enum":["crm","graph8","newest"]},{"type":"null"}],"title":"Authority"},"restricted_acknowledged":{"type":"boolean","title":"Restricted Acknowledged","default":false}},"additionalProperties":false,"type":"object","required":["crm_field","attribute_id"],"title":"ObjectSyncFieldRule","description":"One mapped field. ``authority`` decides a conflict: CRM wins, graph8 wins or the newest change wins."},"ObjectSyncMatch":{"properties":{"crm_field":{"type":"string","maxLength":255,"minLength":1,"title":"Crm Field"},"attribute_id":{"type":"string","format":"uuid","title":"Attribute Id"}},"additionalProperties":false,"type":"object","required":["crm_field","attribute_id"],"title":"ObjectSyncMatch","description":"The explicit match key: a CRM field and a unique graph8 field."},"ObjectSyncNewField":{"properties":{"crm_field":{"type":"string","maxLength":255,"minLength":1,"title":"Crm Field"},"authority":{"anyOf":[{"type":"string","enum":["crm","graph8","newest"]},{"type":"null"}],"title":"Authority"},"direction":{"anyOf":[{"type":"string","enum":["pull","push","both"]},{"type":"null"}],"title":"Direction"},"title":{"anyOf":[{"type":"string","maxLength":200,"minLength":1},{"type":"null"}],"title":"Title"},"api_slug":{"anyOf":[{"type":"string","maxLength":100,"minLength":1,"pattern":"^[a-z][a-z0-9_]*$"},{"type":"null"}],"title":"Api Slug"}},"additionalProperties":false,"type":"object","required":["crm_field"],"title":"ObjectSyncNewField","description":"A CRM field to create a graph8 field for and map; its graph8 type follows from the CRM type."},"ObjectSyncNewMatch":{"properties":{"crm_field":{"type":"string","maxLength":255,"minLength":1,"title":"Crm Field"}},"additionalProperties":false,"type":"object","required":["crm_field"],"title":"ObjectSyncNewMatch"},"ObjectSyncNewObjectSpec":{"properties":{"api_slug":{"anyOf":[{"type":"string","maxLength":100,"minLength":1,"pattern":"^[a-z][a-z0-9_]*$"},{"type":"null"}],"title":"Api Slug"},"singular_noun":{"anyOf":[{"type":"string","maxLength":100,"minLength":1},{"type":"null"}],"title":"Singular Noun"},"plural_noun":{"anyOf":[{"type":"string","maxLength":100,"minLength":1},{"type":"null"}],"title":"Plural Noun"}},"additionalProperties":false,"type":"object","title":"ObjectSyncNewObjectSpec","description":"Names of the new graph8 object; each defaults from the CRM object's label (a taken slug gets a suffix)."},"ObjectSyncRelationshipRule":{"properties":{"relationship_definition_id":{"type":"string","format":"uuid","title":"Relationship Definition Id"},"target_crm_object_id":{"type":"string","maxLength":255,"minLength":1,"title":"Target Crm Object Id"},"crm_field":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Crm Field"},"authority":{"anyOf":[{"type":"string","enum":["crm","graph8"]},{"type":"null"}],"title":"Authority"}},"additionalProperties":false,"type":"object","required":["relationship_definition_id","target_crm_object_id"],"title":"ObjectSyncRelationshipRule","description":"A CRM reference (Salesforce lookup field, HubSpot association) to a graph8 relationship definition.\n\n``authority`` (default ``crm``): ``crm`` = a pull moves the link when the CRM lookup names another record and\nremoves it when the lookup is cleared; ``graph8`` = a pull only adds links (a taken single-valued link is a\n``link_conflict``). A push only ever adds references, whatever the authority."},"ObjectUpdateRequest":{"properties":{"singular_noun":{"anyOf":[{"type":"string","maxLength":100,"minLength":1},{"type":"null"}],"title":"Singular Noun"},"plural_noun":{"anyOf":[{"type":"string","maxLength":100,"minLength":1},{"type":"null"}],"title":"Plural Noun"},"is_archived":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Archived"},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description"},"icon":{"anyOf":[{"type":"string","enum":["box","briefcase","building","calendar","flag","folder","globe","heart","layers","package","target","users"]},{"type":"null"}],"title":"Icon"},"display_attribute_slug":{"anyOf":[{"type":"string","maxLength":100,"minLength":1,"pattern":"^[a-z][a-z0-9_]*$"},{"type":"null"}],"title":"Display Attribute Slug"}},"additionalProperties":false,"type":"object","title":"ObjectUpdateRequest"},"ObjectViewCreate":{"properties":{"title":{"type":"string","maxLength":120,"minLength":1,"title":"Title"},"visibility":{"$ref":"#/components/schemas/Visibility","default":"private"},"state":{"$ref":"#/components/schemas/ObjectViewState"}},"additionalProperties":false,"type":"object","required":["title"],"title":"ObjectViewCreate"},"ObjectViewDefault":{"properties":{"view_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"View Id"}},"additionalProperties":false,"type":"object","title":"ObjectViewDefault"},"ObjectViewState":{"properties":{"version":{"type":"integer","const":1,"title":"Version","default":1},"layout":{"type":"string","enum":["table","board"],"title":"Layout","default":"table"},"filters":{"items":{"$ref":"#/components/schemas/RecordFilter"},"type":"array","maxItems":10,"title":"Filters"},"search":{"type":"string","maxLength":200,"title":"Search","default":""},"sortBy":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sortby"},"sortOrder":{"type":"string","enum":["asc","desc"],"title":"Sortorder","default":"desc"},"includeArchived":{"type":"boolean","title":"Includearchived","default":false},"columns":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":200},{"type":"null"}],"title":"Columns"},"groupBy":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Groupby"}},"additionalProperties":false,"type":"object","title":"ObjectViewState"},"ObjectViewUpdate":{"properties":{"title":{"anyOf":[{"type":"string","maxLength":120,"minLength":1},{"type":"null"}],"title":"Title"},"state":{"anyOf":[{"$ref":"#/components/schemas/ObjectViewState"},{"type":"null"}]}},"additionalProperties":false,"type":"object","title":"ObjectViewUpdate"},"ObjectionCodeFilterGroupDto":{"properties":{"in":{"items":{"type":"string","maxLength":512},"type":"array","maxItems":1000,"title":"In"},"not":{"type":"boolean","title":"Not","default":false}},"additionalProperties":false,"type":"object","title":"ObjectionCodeFilterGroupDto","description":"`objections` — codes live in the PER-ORG `cb_objection_codes` catalog, so\nonly the SHAPE can be checked here. Blank is the one thing the applier\nprovably cannot use."},"OnboardingCatchupRequest":{"properties":{"session_id":{"type":"string","title":"Session Id","description":"The proactive-setup canvas session id."}},"type":"object","required":["session_id"],"title":"OnboardingCatchupRequest","description":"Mirror of `OnboardingCatchupRequest`."},"OnboardingPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"OnboardingPayload","description":"An open envelope for an onboarding or discovery result.\n\nOpen on purpose. Discovery state carries a per-field coverage matrix whose\nfield set is the product's own onboarding questionnaire - it changes as the\nquestionnaire does, and a pinned mirror would silently DROP a field the\ncustomer had answered. On a surface whose whole job is \"what do we still\nnot know about you\", a dropped field reads as an answered question."},"OntologyConceptRequest":{"properties":{"concept_type":{"type":"string","maxLength":100,"minLength":1,"title":"Concept Type"},"concept_id":{"type":"string","maxLength":255,"minLength":1,"title":"Concept Id"},"title":{"type":"string","maxLength":500,"minLength":1,"title":"Title"},"body":{"type":"string","maxLength":2000000,"minLength":1,"title":"Body"},"ontology":{"additionalProperties":true,"type":"object","title":"Ontology"},"trust_tier":{"type":"string","title":"Trust Tier","description":"How much to trust this definition. Defaults to human-reviewed, matching the app — a concept written through the API is treated as authored, not inferred.","default":"human_reviewed"},"source_owner":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Source Owner"},"review_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Review At"},"stale_after":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Stale After","description":"After this, the concept is treated as stale."},"sources":{"items":{"$ref":"#/components/schemas/OntologySource"},"type":"array","maxItems":50,"title":"Sources"},"relationships":{"items":{"$ref":"#/components/schemas/OntologyRelationship"},"type":"array","maxItems":100,"title":"Relationships"},"standard_component_id":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Standard Component Id","description":"The standard-ontology component this maps to, if any."},"definition_override":{"anyOf":[{"type":"string","maxLength":10000},{"type":"null"}],"title":"Definition Override"},"extensions":{"additionalProperties":true,"type":"object","title":"Extensions"}},"type":"object","required":["concept_type","concept_id","title","body"],"title":"OntologyConceptRequest","description":"Define or redefine one concept in the org's ontology."},"OntologyRelationship":{"properties":{},"additionalProperties":true,"type":"object","title":"OntologyRelationship","description":"How one concept relates to another. Open-shaped, matching the app."},"OntologySource":{"properties":{},"additionalProperties":true,"type":"object","title":"OntologySource","description":"Where a concept came from. Open-shaped, matching the app's `SourceInput`."},"OpenSearchAggGroup":{"properties":{"key":{"additionalProperties":true,"type":"object","title":"Key","description":"The group-by field values for this group, e.g. {\"COMPANY_NAICS\": \"3311\", \"COMPANY_STATE\": \"OH\"}."},"agg":{"additionalProperties":true,"type":"object","title":"Agg","description":"Metric values keyed by alias, e.g. {\"count\": 1247, \"unique_domains\": 1184}."}},"type":"object","title":"OpenSearchAggGroup"},"OpenSearchAggSpec":{"properties":{"function":{"type":"string","enum":["count","uniqExact","sum","avg","min","max"],"title":"Function","description":"count=doc count per group; uniqExact=cardinality (HLL-approximate); sum/avg/min/max=numeric metric over `field`.","default":"count"},"field":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Field","description":"RAW UPPERCASE field the metric runs over. Required for every function except `count`. For unique-company counts use uniqExact on COMPANY_ID (the index is contact-grained)."},"alias":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Alias","description":"Output key for this metric in each group's `agg` map. Defaults to `function`."}},"type":"object","title":"OpenSearchAggSpec","description":"A single aggregate metric over the grouped rows.\n\n``count`` needs no field (it is the bucket doc count). All other functions\nrequire ``field``. ``alias`` keys the value in each group's ``agg`` map;\nit defaults to ``function`` when omitted (so two same-function metrics must\neach carry a distinct ``alias``)."},"OpenSearchAggregateRequest":{"properties":{"index":{"type":"string","enum":["mashup_contacts","mashup_companies","hem2contact","ip2company"],"title":"Index","description":"Logical index to aggregate. Maps to a whitelisted physical alias."},"filters":{"additionalProperties":true,"type":"object","title":"Filters","description":"Pre-aggregation equality filters, identical semantics to /opensearch/search. RAW UPPERCASE field names."},"group_by":{"items":{"type":"string"},"type":"array","maxItems":3,"minItems":1,"title":"Group By","description":"1-3 RAW UPPERCASE keyword fields to group on (e.g. [\"COMPANY_NAICS\", \"COMPANY_STATE\"]). Must be keyword-type fields -- the canonical COMPANY_* firmographics are. Capped at 3 dimensions to bound cluster cost. ORDER HIGHEST-CARDINALITY FIRST: deeper dimensions get smaller per-level bucket caps (1000 / 100 / 20), so a low-cardinality field placed last keeps full fidelity while a high-cardinality field placed last may be truncated."},"agg":{"anyOf":[{"items":{"$ref":"#/components/schemas/OpenSearchAggSpec"},"type":"array","maxItems":10},{"type":"null"}],"title":"Agg","description":"Metrics to compute per group (max 10). Defaults to a single `count` when omitted."},"having":{"anyOf":[{"additionalProperties":{"additionalProperties":{"type":"number"},"type":"object"},"type":"object"},{"type":"null"}],"title":"Having","description":"Post-aggregation group filter keyed by metric alias, e.g. {\"count\": {\"gte\": 50}}. Operators: eq, gte, lte, gt, lt."},"sort":{"anyOf":[{"items":{"additionalProperties":{"type":"string"},"type":"object"},"type":"array"},{"type":"null"}],"title":"Sort","description":"Sort the returned groups by a metric alias, e.g. [{\"count\": \"desc\"}]. Applied after `having`."},"limit":{"type":"integer","maximum":1000.0,"minimum":1.0,"title":"Limit","description":"Max number of groups returned (after having + sort). Hard-capped at 1000.","default":100}},"type":"object","required":["index","group_by"],"title":"OpenSearchAggregateRequest","description":"Generic, allowlist-bounded GROUP BY over a whitelisted mashup index.\n\nTranslates to nested OpenSearch ``terms`` aggregations (one level per\n``group_by`` field) with metric sub-aggregations. ``having`` / ``sort`` /\n``limit`` are applied to the flattened groups server-side. Counts from\n``terms`` buckets / ``cardinality`` are APPROXIMATE on a sharded index."},"OpenSearchAggregateResponse":{"properties":{"index":{"type":"string","title":"Index"},"groups":{"items":{"$ref":"#/components/schemas/OpenSearchAggGroup"},"type":"array","title":"Groups","default":[]},"total_groups":{"type":"integer","title":"Total Groups","default":0},"took_ms":{"type":"integer","title":"Took Ms","default":0}},"type":"object","required":["index"],"title":"OpenSearchAggregateResponse"},"OpenSearchCountRequest":{"properties":{"index":{"type":"string","enum":["mashup_contacts","mashup_companies","hem2contact","ip2company"],"title":"Index","description":"Logical index to count. Maps to a whitelisted physical alias."},"filters":{"additionalProperties":true,"type":"object","title":"Filters","description":"Field equality filters, identical semantics to /opensearch/search. Scalar -> term, list -> terms (OR). RAW UPPERCASE field names (e.g. COMPANY_INDUSTRY, COMPANY_NAICS, COMPANY_COUNTRY)."}},"type":"object","required":["index"],"title":"OpenSearchCountRequest","description":"Exact-count request. Same ``index`` + ``filters`` shape as search; the\npage-oriented fields (fields/sort/limit/cursor) are intentionally absent\nbecause a count returns no rows."},"OpenSearchCountResponse":{"properties":{"index":{"type":"string","title":"Index"},"count":{"type":"integer","title":"Count","default":0}},"type":"object","required":["index"],"title":"OpenSearchCountResponse"},"OpenSearchHit":{"properties":{"id":{"type":"string","title":"Id"},"score":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Score"},"source":{"additionalProperties":true,"type":"object","title":"Source","default":{}},"sort":{"anyOf":[{"items":{},"type":"array"},{"type":"null"}],"title":"Sort"}},"type":"object","required":["id"],"title":"OpenSearchHit"},"OpenSearchResolveRequest":{"properties":{"kind":{"type":"string","enum":["hem_to_contact","ip_to_company"],"title":"Kind","description":"Which resolver path to use."},"ids":{"items":{"type":"string"},"type":"array","maxItems":500,"minItems":1,"title":"Ids","description":"Up to 500 input IDs (HEMs or IPs)."}},"type":"object","required":["kind","ids"],"title":"OpenSearchResolveRequest"},"OpenSearchResolveResponse":{"properties":{"kind":{"type":"string","title":"Kind"},"results":{"additionalProperties":{"anyOf":[{"type":"string"},{"type":"null"}]},"type":"object","title":"Results","default":{}},"matched":{"type":"integer","title":"Matched","default":0},"requested":{"type":"integer","title":"Requested","default":0}},"type":"object","required":["kind"],"title":"OpenSearchResolveResponse"},"OpenSearchSearchRequest":{"properties":{"index":{"type":"string","enum":["mashup_contacts","mashup_companies","hem2contact","ip2company"],"title":"Index","description":"Logical index to search. Maps to a whitelisted physical alias."},"filters":{"additionalProperties":true,"type":"object","title":"Filters","description":"Field equality filters. Scalar value -> term, list -> terms (OR). Use this to narrow by COMPANY_DOMAIN, COMPANY_INDUSTRY, hem, etc. Field names are the RAW index fields (UPPERCASE, e.g. COMPANY_INDUSTRY) -- not the friendly snake_case names used by /search."},"fields":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Fields","description":"Optional projection. If omitted, returns the full _source. Pass a list to reduce payload size when the LLM only needs a few columns."},"sort":{"anyOf":[{"items":{"additionalProperties":{"type":"string"},"type":"object"},"type":"array"},{"type":"null"}],"title":"Sort","description":"Optional sort, list of `{field: 'asc'|'desc'}`. Required if you intend to paginate via cursor."},"limit":{"type":"integer","maximum":200.0,"minimum":1.0,"title":"Limit","description":"Hard-capped at 200.","default":50},"cursor":{"anyOf":[{"items":{},"type":"array"},{"type":"null"}],"title":"Cursor","description":"search_after token returned from a prior page. Pair with `sort`."},"track_total_hits":{"anyOf":[{"type":"integer","maximum":1000000.0,"minimum":1.0},{"type":"null"}],"title":"Track Total Hits","description":"Exact-count ceiling for the returned `total`. OMIT for the default behaviour (OpenSearch saturates `total` at 10000). Pass an integer ceiling 1-1000000 (e.g. 100000) to get an exact `total` up to that bound in the SAME round trip as the page. For a count with no page payload prefer POST /opensearch/count. Does NOT lift the from+size pagination depth -- use `cursor` (search_after) for that. (0 is rejected: it would mean 'disable tracking' in OpenSearch, which is what omitting it does.)"}},"type":"object","required":["index"],"title":"OpenSearchSearchRequest"},"OpenSearchSearchResponse":{"properties":{"index":{"type":"string","title":"Index"},"total":{"type":"integer","title":"Total","default":0},"hits":{"items":{"$ref":"#/components/schemas/OpenSearchHit"},"type":"array","title":"Hits","default":[]},"cursor":{"anyOf":[{"items":{},"type":"array"},{"type":"null"}],"title":"Cursor"},"took_ms":{"type":"integer","title":"Took Ms","default":0}},"type":"object","required":["index"],"title":"OpenSearchSearchResponse"},"OperatingModelRequest":{"properties":{"override":{"additionalProperties":true,"type":"object","title":"Override","description":"The organisation's operating-model override, REPLACED WHOLE. This is a PUT: keys absent from the body are removed, not left alone. Read `GET /agent/operators/operating-model` first and send it back modified."}},"type":"object","required":["override"],"title":"OperatingModelRequest","description":"Mirror of `OperatingModelUpdate`.\n\n`override` is an open object and stays that way. It is the organisation's\noperating-model document - which motions it runs, what it calls them - and\nit is validated by the service against the live model definition rather\nthan by a shape frozen into this contract. Pinning it would refuse a key a\nnewer platform version understands."},"OperatorApprovalDecisionRequest":{"properties":{"resolution":{"type":"string","enum":["approved","rejected"],"title":"Resolution","description":"`approved` EXECUTES the finding's proposed fix against your data; `rejected` records the decision and executes nothing."},"params":{"anyOf":[{"additionalProperties":{"type":"string"},"type":"object"},{"type":"null"}],"title":"Params","description":"Values a fix needs that the operator could not decide for you, e.g. `{\"target_user\": \"<user id>\"}`. Omit for a fully-specified fix. A value the fix refuses is a 400 naming the field, and the task stays open."}},"type":"object","required":["resolution"],"title":"OperatorApprovalDecisionRequest","description":"Mirror of `ApprovalDecision`.\n\n`resolution` is closed to the two values the app accepts. The app answers\nanything else with a 400 after lower-casing it; closing it here makes a bad\nvalue a 422 that names the valid ones."},"OperatorEnabledRequest":{"properties":{"enabled":{"type":"boolean","title":"Enabled","description":"Whether this operator runs for the organisation. TURNING IT ON STARTS UNATTENDED WORK: the operator's monitors run on their own schedule from then on, without a person asking. Explicit rather than a toggle, so a retried request is idempotent instead of flipping the state back."}},"type":"object","required":["enabled"],"title":"OperatorEnabledRequest","description":"Mirror of `EnabledUpdate`."},"OperatorListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"OperatorListPayload","description":"An open envelope for a LIST answer, so a bare list keeps its shape."},"OperatorPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"OperatorPayload","description":"An open envelope for one operator answer.\n\nOpen because an operator's health snapshot, scorecard and catalog are\nper-operator documents whose shape follows what that operator monitors -\nthe revenue operator reports different checks from the deliverability one,\nand both grow. On an OVERSIGHT surface a dropped field reads as \"nothing to\nworry about\" rather than \"we did not tell you\", which is the failure mode\nworth designing against."},"OperatorRecipientRequest":{"properties":{"user_id":{"type":"string","title":"User Id","description":"The person who receives this operator's alerts and owns its approval tasks. One recipient per operator: setting it REPLACES whoever was there."}},"type":"object","required":["user_id"],"title":"OperatorRecipientRequest","description":"Mirror of `RecipientUpdate`."},"OperatorTrustDialRequest":{"properties":{"autonomy":{"type":"string","enum":["OFF","DETECT","PROPOSE","AUTO"],"title":"Autonomy","description":"How far this skill may go on its own. `OFF` - do not run it. `DETECT` - look, and record what it finds. `PROPOSE` - look, and raise an approval task a person decides. `AUTO` - act and log, with no human in the loop. THIS IS A REQUEST, NOT A GUARANTEE: the effective level is the MINIMUM of this dial, the skill's own graph8-managed risk cap and the platform ceiling, so a skill capped at `PROPOSE` stays at `PROPOSE` however this is set. Read the response, and `GET /agent/operators/{operator}/skills`, for what the dial actually resolved to."}},"type":"object","required":["autonomy"],"title":"OperatorTrustDialRequest","description":"Mirror of `TrustDialUpdate`, with `autonomy` closed to the shipped set."},"OpportunityApplyRequest":{"properties":{"cover_letter":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Cover Letter"},"resume_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Resume Url","description":"Omit to use your profile resume."}},"type":"object","title":"OpportunityApplyRequest","description":"Easy-apply to a published role.\n\n`resume_url` defaults to the resume already on your profile; with neither,\nthe app refuses with a 422 naming the missing resume."},"OpsActionRow":{"properties":{"action_id":{"type":"string","title":"Action Id"},"sequence_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Id"},"sequence_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Name"},"step_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Step Id"},"kind":{"type":"string","title":"Kind","description":"INVITE | MESSAGE"},"action_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Action Type","description":"CONNECTION_REQUEST | MESSAGE"},"status":{"type":"string","title":"Status","description":"QUEUED | SENDING | SENT | ACCEPTED | FAILED. A FAILED INVITE with failure_reason `withdrawn` reached LinkedIn and was later withdrawn unanswered by the provider."},"source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source","description":"SEQUENCER | WORKFLOW | AI_INBOX"},"target_identifier":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Identifier","description":"Prospect LinkedIn slug (PII)"},"note":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Note","description":"Connection-request note, POST-RENDER. Null is the NORM for bare-invite plays (intentional strategy) — never report a null note as missing data."},"message_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Message Text","description":"Rendered message body. Null for INVITE rows by design."},"degree_observed":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Degree Observed","description":"Connection degree arlink observed; only set after a provider round-trip."},"failure_reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Failure Reason","description":"COALESCE of the executed-step skip_reason (richer) and the queue row's last_error. `skipped_too_distant` = target not 1st/2nd-degree reachable — an ELIGIBILITY skip, not a provider error or account-health problem."},"attempts":{"type":"integer","title":"Attempts","default":0},"budget_day":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Budget Day"},"requested_at":{"type":"string","format":"date-time","title":"Requested At"},"due_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Due At"},"sent_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Sent At"},"resolved_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Resolved At"},"sender_account_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sender Account Id"},"sender_display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sender Display Name"},"sender_public_identifier":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sender Public Identifier"},"contact_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Contact Id"},"contact_first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contact First Name","description":"PII"},"contact_last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contact Last Name","description":"PII"},"contact_linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contact Linkedin Url","description":"PII"},"contact_job_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contact Job Title","description":"PII"},"contact_work_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contact Work Email","description":"PII; ~87% populated"},"company_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Company Id"},"company_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Name","description":"~49% populated (company-enrichment gap) — never assume present."},"contact_seq_state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contact Seq State","description":"seqsequencecontacts.state. `waiting_netrion` = parked with a live queue row outstanding. `skipped` = channel skip (e.g. no LinkedIn URL), NOT a send."},"contact_current_step_order":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Contact Current Step Order"}},"type":"object","required":["action_id","kind","status","requested_at"],"title":"OpsActionRow","description":"One `linkedin_action_queue` row with its full per-contact drill-down."},"OpsActionSummaryRow":{"properties":{"sequence_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Id"},"sequence_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Name"},"account_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Id"},"sender_display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sender Display Name"},"kind":{"type":"string","title":"Kind"},"status":{"type":"string","title":"Status"},"count":{"type":"integer","title":"Count"},"first_requested_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"First Requested At"},"last_requested_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Last Requested At"},"last_sent_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Last Sent At"}},"type":"object","required":["kind","status","count"],"title":"OpsActionSummaryRow","description":"One cell of the sequence × sender × kind × status matrix."},"OpsIndex":{"properties":{"description":{"type":"string","title":"Description"},"org_id_formats":{"type":"string","title":"Org Id Formats"},"resources":{"items":{"$ref":"#/components/schemas/OpsIndexEntry"},"type":"array","title":"Resources"}},"type":"object","required":["description","org_id_formats","resources"],"title":"OpsIndex","description":"Self-describing index so an LLM consumer can discover the surface\nwithout parsing the full OpenAPI document."},"OpsIndexEntry":{"properties":{"resource":{"type":"string","title":"Resource"},"path":{"type":"string","title":"Path"},"description":{"type":"string","title":"Description"}},"type":"object","required":["resource","path","description"],"title":"OpsIndexEntry"},"OpsSequenceBindingRow":{"properties":{"sequence_id":{"type":"string","title":"Sequence Id"},"sequence_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Name"},"sequence_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Status"},"is_archived":{"type":"boolean","title":"Is Archived","default":false},"owner_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Email","description":"Internal team member (PII, low sensitivity)"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"paused_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Paused At"},"resumed_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Resumed At"},"channel_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Channel Id"},"sender_public_identifier":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sender Public Identifier"},"bound_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Bound At"},"account_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Id","description":"arlink lia_... id"},"account_display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Display Name"},"account_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Status","description":"OK = healthy. Only `deletedAt IS NULL AND status='OK'` counts as connected."},"invite_daily_cap":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Invite Daily Cap"},"message_daily_cap":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Message Daily Cap"},"contact_state_counts":{"additionalProperties":{"type":"integer"},"type":"object","title":"Contact State Counts","description":"seqsequencecontacts states for this sequence. Absent state = 0. `waiting_netrion` is the in-flight park state."}},"type":"object","required":["sequence_id"],"title":"OpsSequenceBindingRow","description":"One live sequence↔sender binding (`channel_type='LINKEDIN_NETRION'`)."},"OpsSequenceBindingsReport":{"properties":{"bound":{"items":{"$ref":"#/components/schemas/OpsSequenceBindingRow"},"type":"array","title":"Bound"},"unbound_live_sequences":{"items":{"$ref":"#/components/schemas/OpsUnboundSequenceRow"},"type":"array","title":"Unbound Live Sequences"}},"type":"object","required":["bound","unbound_live_sequences"],"title":"OpsSequenceBindingsReport"},"OpsUnboundSequenceRow":{"properties":{"sequence_id":{"type":"string","title":"Sequence Id"},"sequence_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Name"},"sequence_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Status"},"owner_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Email"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"}},"type":"object","required":["sequence_id"],"title":"OpsUnboundSequenceRow","description":"A live, non-archived sequence with a NETRION step but NO active channel\nbinding — configured but can never send. This is the population behind\n'connected but not sending'."},"OpsWebhookEventSummary":{"properties":{"event":{"type":"string","title":"Event"},"count":{"type":"integer","title":"Count"},"first_seen":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"First Seen"},"last_seen":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Last Seen"}},"type":"object","required":["event","count"],"title":"OpsWebhookEventSummary","description":"Per-event-type aggregate. The events table stores NO payload (dedupe\nledger only) — to learn *what happened*, read the effects instead:\n`linkedin_action_queue.status` and the contact's sequencer state.\n\n`inbox.message_received` is NOT a sequence reply — only `lead.message_received`\ncarries reply semantics. Never conflate the two counts."},"OrderSpec":{"properties":{"mode":{"type":"string","enum":["natural_skip_dialed","dialed_first"],"title":"Mode","default":"natural_skip_dialed"},"phone_priority":{"items":{"type":"string"},"type":"array","title":"Phone Priority"},"sort_model":{"items":{"additionalProperties":{"type":"string"},"type":"object"},"type":"array","title":"Sort Model"}},"type":"object","title":"OrderSpec","description":"The order the queue is worked in, and which phone field is tried first."},"OrgCostSettingsRequest":{"properties":{"version":{"type":"integer","title":"Version","default":1},"enabled":{"type":"boolean","title":"Enabled","default":false},"employees":{"additionalProperties":{"$ref":"#/components/schemas/EmployeeCost"},"type":"object","title":"Employees"},"commission":{"$ref":"#/components/schemas/CommissionConfig"}},"type":"object","title":"OrgCostSettingsRequest","description":"Labour cost per rep and the commission model. REPLACES the stored config."},"OrgCsatBlockDTO":{"properties":{"csat_avg":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Csat Avg"},"total_respondents":{"type":"integer","title":"Total Respondents"}},"type":"object","required":["total_respondents"],"title":"OrgCsatBlockDTO"},"OrgDeliverabilityProtectionRequest":{"properties":{"version":{"type":"integer","const":1,"title":"Version","default":1},"enabled":{"type":"boolean","title":"Enabled","default":true},"categories":{"items":{"type":"string"},"type":"array","title":"Categories"}},"type":"object","title":"OrgDeliverabilityProtectionRequest","description":"Which high-risk content categories are blocked before a send."},"OrgDepartmentsUpdateRequest":{"properties":{"entries":{"items":{"$ref":"#/components/schemas/DepartmentEntry"},"type":"array","maxItems":100,"title":"Entries"}},"type":"object","required":["entries"],"title":"OrgDepartmentsUpdateRequest","description":"The department taxonomy. REPLACES the whole list."},"OrgDialerTargetsRequest":{"properties":{"daily_dials_target":{"type":"integer","minimum":0.0,"title":"Daily Dials Target","default":250},"daily_meetings_target":{"type":"integer","minimum":0.0,"title":"Daily Meetings Target","default":3},"updated_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated By"}},"type":"object","title":"OrgDialerTargetsRequest","description":"Org-wide daily goals. Voice takes these as QUERY params; they are a\nbody here because they are a record being written, not a filter."},"OrgEventFeedPage":{"properties":{"events":{"items":{"$ref":"#/components/schemas/OrgEventItem"},"type":"array","title":"Events"},"next_cursor":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Next Cursor","description":"Pass back as `cursor` to fetch the next (older) page. Null when there are no more."},"has_more":{"type":"boolean","title":"Has More","description":"Whether another page exists within the requested window.","default":false},"since":{"type":"string","title":"Since","description":"Lower bound of the window that was searched (ISO 8601, UTC)."},"until":{"type":"string","title":"Until","description":"Upper bound of the window that was searched (ISO 8601, UTC)."}},"type":"object","required":["since","until"],"title":"OrgEventFeedPage","description":"A page of events, newest first."},"OrgEventItem":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id","description":"Event uid. Stable across reads; use it to de-duplicate."},"type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Type","description":"Event family, e.g. sequencer, inbox, voiceai, appointments, crm, deals, quotes, newsletter, uui, mcp, internal. Web-tracking rows carry the tracker's type (e.g. page)."},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Event name, e.g. sequence_email_sent, inbox.email_received, sdr.call_ended, booking_created."},"source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source","description":"Producing service, e.g. sequencer, voiceai-service."},"occurred_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Occurred At","description":"When the event happened (ISO 8601, UTC)."},"actor_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Actor Email","description":"The event's context email: the acting user, recipient or a system actor address."},"contact_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contact Id","description":"message.contact_id, when the event carries one."},"sequence_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Id","description":"message.sequence_id, when the event carries one."},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id","description":"message.campaign_id, when the event carries one."},"url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Url","description":"Page URL, for web-tracking rows."},"message":{"additionalProperties":true,"type":"object","title":"Message","description":"The event payload exactly as produced."}},"type":"object","title":"OrgEventItem","description":"One event from the org's event store."},"OrgGovernancePayload":{"properties":{},"additionalProperties":true,"type":"object","title":"OrgGovernancePayload","description":"A settings view or the result of a change, as the app returns it."},"OrgInfrastructureSelection":{"properties":{"provider_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Provider Ids"},"custom_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Custom Name","description":"Used when `other` is among `provider_ids`."},"notes":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Notes"}},"type":"object","title":"OrgInfrastructureSelection"},"OrgListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"OrgListPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape.\n\nMost of these handlers return a bare `list[...]`; a few return a named\nenvelope (`{\"team_members\": [...], \"total\": n}`). Both are reachable as\n`items`, and a named envelope KEEPS its own key as well so a caller\nalready reading the app's shape is not broken by the wrapper."},"OrgMeetingUpdateRequest":{"properties":{"status":{"anyOf":[{"type":"string","enum":["scheduled","taken","rescheduled","missed","cancelled"]},{"type":"null"}],"title":"Status"},"meeting_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Meeting Date","description":"YYYY-MM-DD."},"meeting_type":{"anyOf":[{"type":"string","enum":["discovery","demo","follow_up","closing"]},{"type":"null"}],"title":"Meeting Type"},"notes":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Notes"},"client_contact_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Client Contact Name"},"client_contact_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Client Contact Email"}},"type":"object","title":"OrgMeetingUpdateRequest","description":"The client's edit of a meeting its hire ran. Unset fields are untouched.\n\nSetting `status` to `taken` is the BILLING SIGNAL: that row becomes\nchargeable at the engagement's per-meeting rate, and the talent is notified.\nMoving `meeting_date` without a `status` flips the row to `rescheduled`.\nBoth vocabularies are closed here so a typo is a 422 naming the valid values\nrather than the app's 400."},"OrgNpsBlockDTO":{"properties":{"nps_score":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Nps Score"},"promoters":{"type":"integer","title":"Promoters"},"passives":{"type":"integer","title":"Passives"},"detractors":{"type":"integer","title":"Detractors"},"total_respondents":{"type":"integer","title":"Total Respondents"}},"type":"object","required":["promoters","passives","detractors","total_respondents"],"title":"OrgNpsBlockDTO"},"OrgOutboundTrackingRequest":{"properties":{"version":{"type":"integer","title":"Version","default":1},"enabled":{"type":"boolean","title":"Enabled","default":false},"utm_source_prefix":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Utm Source Prefix"},"channels":{"$ref":"#/components/schemas/OutboundTrackingChannels"}},"type":"object","title":"OrgOutboundTrackingRequest","description":"UTM tagging of outbound links, per channel."},"OrgPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"OrgPayload","description":"An open envelope for a single role, team, member or account record.\n\nOpen on purpose. The app's own response models on this surface grow with\nthe product - `RoleResponse` gained `rep_limits` and `manages_role_slugs`,\n`TeamResponse` gained channel counts and a campaign count - and a pinned\nmirror would SILENTLY DROP whatever it had not caught up on. A dropped\npermission in a role read is the worst possible kind of stale: it reads as\n\"they do not have it\"."},"OrgSettingsUpdateRequest":{"properties":{"org_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Org Name","description":"Organization display name. PropelAuth owns it; a rejected rename aborts the whole update."},"email_domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email Domain","description":"Email domain for auto-join signup (e.g. `graph8.com`). Anyone who signs up with an address at this domain joins this organization with no invite. Normalised: scheme, `www.` and trailing slash are stripped and the value is lowercased."}},"type":"object","title":"OrgSettingsUpdateRequest","description":"Mirrors `campaign_builder.routers.org_settings.UpdateOrgSettingsRequest`.\n\n`email_domain` is the auto-join domain: anyone signing up with an address\nat that domain joins THIS organisation without an invite. It is the widest\nblast radius on this surface, which is why the route is admin-gated and the\nhandler re-checks the caller's org role on top."},"OrgSummaryDTO":{"properties":{"org_nps":{"$ref":"#/components/schemas/OrgNpsBlockDTO"},"org_csat":{"$ref":"#/components/schemas/OrgCsatBlockDTO"},"in_app_respondents":{"type":"integer","title":"In App Respondents","default":0},"in_app_csat_avg":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"In App Csat Avg"},"segment":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Segment"},"per_survey":{"items":{"$ref":"#/components/schemas/PerSurveyDTO"},"type":"array","title":"Per Survey"},"bucket":{"type":"string","title":"Bucket"},"time_series":{"items":{"$ref":"#/components/schemas/TrendBarDTO"},"type":"array","title":"Time Series"}},"type":"object","required":["org_nps","org_csat","per_survey","bucket","time_series"],"title":"OrgSummaryDTO"},"OrgVideoGenerateRequest":{"properties":{"template_id":{"type":"string","maxLength":40,"minLength":1,"title":"Template Id","default":"plain"},"storyboard":{"$ref":"#/components/schemas/OrgVideoStoryboard"},"title":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Title"}},"type":"object","required":["storyboard"],"title":"OrgVideoGenerateRequest"},"OrgVideoListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"OrgVideoListPayload","description":"The org's library videos under `items`."},"OrgVideoPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"OrgVideoPayload","description":"A library video. `generation` carries render progress for generated videos."},"OrgVideoShot":{"properties":{"clip_id":{"type":"string","title":"Clip Id","description":"A READY Studio clip."},"in_s":{"anyOf":[{"type":"number","minimum":0.0},{"type":"null"}],"title":"In S","description":"Trim start, seconds."},"out_s":{"anyOf":[{"type":"number","exclusiveMinimum":0.0},{"type":"null"}],"title":"Out S","description":"Trim end, seconds."}},"type":"object","required":["clip_id"],"title":"OrgVideoShot"},"OrgVideoStoryboard":{"properties":{"shots":{"items":{"$ref":"#/components/schemas/OrgVideoShot"},"type":"array","title":"Shots"},"copy":{"additionalProperties":{"type":"string"},"type":"object","title":"Copy","description":"Copy slot id -> text. The `plain` template renders none."}},"type":"object","title":"OrgVideoStoryboard"},"OrgVideoUpdateRequest":{"properties":{"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"alt_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Alt Text"},"poster_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Poster Url"},"tags":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Tags"}},"type":"object","title":"OrgVideoUpdateRequest"},"OutboundTrackingChannels":{"properties":{"email":{"type":"boolean","title":"Email","default":false},"linkedin":{"type":"boolean","title":"Linkedin","default":false},"whatsapp":{"type":"boolean","title":"Whatsapp","default":false},"sms":{"type":"boolean","title":"Sms","default":false},"voice":{"type":"boolean","title":"Voice","default":false},"dialer":{"type":"boolean","title":"Dialer","default":false}},"type":"object","title":"OutboundTrackingChannels","description":"Per-channel UTM injection toggles. email, linkedin, and whatsapp are\nwired into their send paths; sms/voice/dialer use booking-link tokens."},"OutboxListResponse":{"properties":{"sandbox":{"type":"boolean","title":"Sandbox","default":true},"items":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Items"},"count":{"type":"integer","title":"Count"}},"type":"object","required":["items","count"],"title":"OutboxListResponse"},"OutputColumnDef":{"properties":{"name":{"type":"string","maxLength":255,"minLength":1,"title":"Name"},"type":{"type":"string","title":"Type","default":"text"},"display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display Name"},"mapping_target":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mapping Target"}},"type":"object","required":["name"],"title":"OutputColumnDef","description":"One column an AI pass writes into."},"OutreachAddLeadsRequest":{"properties":{"leads":{"items":{"additionalProperties":true,"type":"object"},"type":"array","minItems":1,"title":"Leads"}},"type":"object","required":["leads"],"title":"OutreachAddLeadsRequest","description":"People to add to an outreach lead list.\n\nEach object is one person. `linkedInUrl`, `firstName` and `lastName` are the\nfields that matter; `companyName`, `position` and similar are passed through."},"OutreachCampaign":{"properties":{"id":{"type":"integer","title":"Id"},"name":{"type":"string","title":"Name"},"status":{"type":"string","title":"Status","description":"DRAFT, ONGOING, PAUSED or FINISHED."},"total_leads":{"type":"integer","title":"Total Leads","default":0},"pending_leads":{"type":"integer","title":"Pending Leads","default":0},"finished_leads":{"type":"integer","title":"Finished Leads","default":0},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"}},"type":"object","required":["id","name","status"],"title":"OutreachCampaign"},"OutreachCampaignActionResult":{"properties":{"success":{"type":"boolean","title":"Success"},"message":{"type":"string","title":"Message"}},"type":"object","required":["success","message"],"title":"OutreachCampaignActionResult"},"OutreachCampaignLead":{"properties":{"id":{"type":"integer","title":"Id"},"linkedin_user_profile_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin User Profile Id"},"linkedin_user_profile":{"anyOf":[{"$ref":"#/components/schemas/OutreachLeadProfile"},{"type":"null"}]},"last_action_time":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Action Time"},"failed_time":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Failed Time"},"creation_time":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Creation Time"},"lead_campaign_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Lead Campaign Status"},"lead_connection_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Lead Connection Status"},"lead_message_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Lead Message Status"},"error_code":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Error Code"},"lead_campaign_status_message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Lead Campaign Status Message"},"linkedin_sender_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Linkedin Sender Id"},"linkedin_sender_full_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Sender Full Name"}},"type":"object","required":["id"],"title":"OutreachCampaignLead"},"OutreachCampaignLeads":{"properties":{"total_count":{"type":"integer","title":"Total Count"},"items":{"items":{"$ref":"#/components/schemas/OutreachCampaignLead"},"type":"array","title":"Items"},"offset":{"type":"integer","title":"Offset"},"limit":{"type":"integer","title":"Limit"}},"type":"object","required":["total_count","items","offset","limit"],"title":"OutreachCampaignLeads"},"OutreachCampaignLeadsQuery":{"properties":{"campaign_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Campaign Id","description":"Ignored; the path value is used."},"offset":{"type":"integer","title":"Offset","description":"Leads to skip.","default":0},"limit":{"type":"integer","title":"Limit","description":"Page size. Values above 1000 are capped at 1000.","default":100},"time_from":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Time From","description":"ISO 8601."},"time_to":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Time To","description":"ISO 8601."},"time_filter":{"anyOf":[{"type":"string","enum":["CreationTime","Everywhere"]},{"type":"null"}],"title":"Time Filter"}},"type":"object","title":"OutreachCampaignLeadsQuery","description":"Page through the people in one campaign. Reads only.\n\n`campaign_id` exists because the app's model has it; the PATH value is\nauthoritative and overwrites whatever is sent here."},"OutreachCampaignProgress":{"properties":{"campaign_id":{"type":"integer","title":"Campaign Id"},"campaign_name":{"type":"string","title":"Campaign Name"},"status":{"title":"Status"},"progress_stats":{"$ref":"#/components/schemas/OutreachProgressFigures"}},"type":"object","required":["campaign_id","campaign_name","progress_stats"],"title":"OutreachCampaignProgress"},"OutreachCampaignStats":{"properties":{"stats":{"$ref":"#/components/schemas/OutreachCampaignStatsFigures"},"by_day_stats":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"By Day Stats"}},"type":"object","required":["stats"],"title":"OutreachCampaignStats"},"OutreachCampaignStatsFigures":{"properties":{"campaign_id":{"type":"integer","title":"Campaign Id"},"profile_views":{"type":"integer","title":"Profile Views","default":0},"post_likes":{"type":"integer","title":"Post Likes","default":0},"follows":{"type":"integer","title":"Follows","default":0},"messages_sent":{"type":"integer","title":"Messages Sent","default":0},"total_message_started":{"type":"integer","title":"Total Message Started","default":0},"total_message_replies":{"type":"integer","title":"Total Message Replies","default":0},"inmail_messages_sent":{"type":"integer","title":"Inmail Messages Sent","default":0},"connections_sent":{"type":"integer","title":"Connections Sent","default":0},"connections_accepted":{"type":"integer","title":"Connections Accepted","default":0},"message_reply_rate":{"type":"number","title":"Message Reply Rate","default":0.0},"connection_acceptance_rate":{"type":"number","title":"Connection Acceptance Rate","default":0.0}},"type":"object","required":["campaign_id"],"title":"OutreachCampaignStatsFigures"},"OutreachCampaigns":{"properties":{"campaigns":{"items":{"$ref":"#/components/schemas/OutreachCampaign"},"type":"array","title":"Campaigns"},"total_count":{"type":"integer","title":"Total Count"}},"type":"object","required":["campaigns","total_count"],"title":"OutreachCampaigns"},"OutreachConnectionStatus":{"properties":{"connected":{"type":"boolean","title":"Connected"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"},"tenant_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Tenant Id"},"token_expires_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Token Expires At"},"is_token_valid":{"type":"boolean","title":"Is Token Valid","default":false},"time_until_expiry_seconds":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Time Until Expiry Seconds"},"auto_reauth_enabled":{"type":"boolean","title":"Auto Reauth Enabled","default":false},"auto_reauth_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Auto Reauth Status"},"failed_reauth_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Failed Reauth Count"},"last_reauth_success_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Reauth Success At"},"auto_reauth_error":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Auto Reauth Error"},"requires_manual_login":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Requires Manual Login"},"reenable_in_seconds":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Reenable In Seconds"},"workspace_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Workspace Id"},"workspace_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Workspace Name"},"workspace_configured":{"type":"boolean","title":"Workspace Configured","default":false}},"type":"object","required":["connected"],"title":"OutreachConnectionStatus","description":"Whether the org's outreach connection exists and its session is healthy. Never the credentials."},"OutreachLeadProfile":{"properties":{"linkedin_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Id"},"profile_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Profile Url"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"headline":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Headline"},"image_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Image Url"},"location":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Location"},"company_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Name"},"company_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Url"},"position":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Position"},"about":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"About"},"connections":{"type":"integer","title":"Connections","default":0},"followers":{"type":"integer","title":"Followers","default":0},"email_address":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email Address"}},"type":"object","title":"OutreachLeadProfile"},"OutreachLeadsAdded":{"properties":{"added_count":{"type":"integer","title":"Added Count"}},"type":"object","required":["added_count"],"title":"OutreachLeadsAdded"},"OutreachList":{"properties":{"id":{"type":"integer","title":"Id"},"name":{"type":"string","title":"Name"},"leads_count":{"type":"integer","title":"Leads Count","default":0},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"}},"type":"object","required":["id","name"],"title":"OutreachList"},"OutreachListCreateRequest":{"properties":{"name":{"type":"string","minLength":1,"title":"Name"}},"type":"object","required":["name"],"title":"OutreachListCreateRequest","description":"A new, empty lead list on the outreach platform."},"OutreachListCreated":{"properties":{"id":{"type":"integer","title":"Id"},"name":{"type":"string","title":"Name"}},"type":"object","required":["id","name"],"title":"OutreachListCreated"},"OutreachLists":{"properties":{"lists":{"items":{"$ref":"#/components/schemas/OutreachList"},"type":"array","title":"Lists"},"total_count":{"type":"integer","title":"Total Count"}},"type":"object","required":["lists","total_count"],"title":"OutreachLists"},"OutreachProgressFigures":{"properties":{"total_users":{"type":"integer","title":"Total Users","default":0},"total_users_in_progress":{"type":"integer","title":"Total Users In Progress","default":0},"total_users_pending":{"type":"integer","title":"Total Users Pending","default":0},"total_users_finished":{"type":"integer","title":"Total Users Finished","default":0},"total_users_failed":{"type":"integer","title":"Total Users Failed","default":0},"total_users_manually_stopped":{"type":"integer","title":"Total Users Manually Stopped","default":0},"total_users_excluded":{"type":"integer","title":"Total Users Excluded","default":0}},"type":"object","title":"OutreachProgressFigures"},"OutreachReconnectResult":{"properties":{"success":{"type":"boolean","title":"Success"},"message":{"type":"string","title":"Message"},"requires_login":{"type":"boolean","title":"Requires Login","default":false},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"},"token_expires_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Token Expires At"}},"type":"object","required":["success","message"],"title":"OutreachReconnectResult","description":"Outcome of refreshing the session. `requires_login: true` means a person must sign in again in the app."},"OutreachSenderAccount":{"properties":{"id":{"type":"integer","title":"Id"},"name":{"type":"string","title":"Name"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"},"profile_picture_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Profile Picture Url"},"is_connected":{"type":"boolean","title":"Is Connected","default":true},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"is_premium":{"type":"boolean","title":"Is Premium","default":false}},"type":"object","required":["id","name"],"title":"OutreachSenderAccount","description":"A LinkedIn account that sends outreach."},"OutreachSenderAccounts":{"properties":{"accounts":{"items":{"$ref":"#/components/schemas/OutreachSenderAccount"},"type":"array","title":"Accounts"},"total_count":{"type":"integer","title":"Total Count"}},"type":"object","required":["accounts","total_count"],"title":"OutreachSenderAccounts"},"OutreachSequenceMapping":{"properties":{"sequence_id":{"type":"string","title":"Sequence Id"},"campaign_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Campaign Id"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"campaign_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Name"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"}},"type":"object","required":["sequence_id"],"title":"OutreachSequenceMapping","description":"The outreach campaign and list a graph8 sequence runs through."},"OutreachStepCampaign":{"properties":{"campaign_id":{"type":"integer","title":"Campaign Id"},"status":{"type":"string","title":"Status"},"linkedin_action_type":{"type":"string","title":"Linkedin Action Type"}},"type":"object","required":["campaign_id","status","linkedin_action_type"],"title":"OutreachStepCampaign"},"OutreachStepCampaigns":{"properties":{"step_campaigns":{"additionalProperties":{"$ref":"#/components/schemas/OutreachStepCampaign"},"type":"object","title":"Step Campaigns"}},"type":"object","required":["step_campaigns"],"title":"OutreachStepCampaigns","description":"Keyed by sequence step id. Steps with no campaign are absent."},"OutreachTemplate":{"properties":{"id":{"type":"integer","title":"Id"},"name":{"type":"string","title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"sequence":{"additionalProperties":true,"type":"object","title":"Sequence"},"is_default":{"type":"boolean","title":"Is Default","default":false}},"type":"object","required":["id","name","sequence"],"title":"OutreachTemplate"},"OutreachTemplates":{"properties":{"templates":{"items":{"$ref":"#/components/schemas/OutreachTemplate"},"type":"array","title":"Templates"}},"type":"object","required":["templates"],"title":"OutreachTemplates"},"OutreachWorkspace":{"properties":{"workspace_id":{"type":"integer","title":"Workspace Id"},"workspace_name":{"type":"string","title":"Workspace Name"},"seats_limit":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Seats Limit"},"used_seats":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Used Seats"}},"type":"object","required":["workspace_id","workspace_name"],"title":"OutreachWorkspace"},"OutreachWorkspaceSelectRequest":{"properties":{"workspace_id":{"type":"integer","title":"Workspace Id","description":"A `workspace_id` from `GET /integrations/linkedin-outreach/workspaces`."}},"type":"object","required":["workspace_id"],"title":"OutreachWorkspaceSelectRequest","description":"Which workspace this org sends from. ONE-TIME: it cannot be changed once set."},"OutreachWorkspaceSelected":{"properties":{"success":{"type":"boolean","title":"Success"},"workspace_id":{"type":"integer","title":"Workspace Id"},"workspace_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Workspace Name"},"message":{"type":"string","title":"Message"}},"type":"object","required":["success","workspace_id","message"],"title":"OutreachWorkspaceSelected"},"OutreachWorkspaceState":{"properties":{"connected":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Connected"},"success":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Success"},"workspace_configured":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Workspace Configured"},"workspace_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Workspace Id"},"workspace_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Workspace Name"},"message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Message"}},"type":"object","title":"OutreachWorkspaceState","description":"The workspace this org sends from, if one is selected."},"OutreachWorkspaces":{"properties":{"workspaces":{"items":{"$ref":"#/components/schemas/OutreachWorkspace"},"type":"array","title":"Workspaces"},"total_count":{"type":"integer","title":"Total Count"},"current_workspace_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Current Workspace Id"},"current_workspace_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Current Workspace Name"}},"type":"object","required":["workspaces","total_count"],"title":"OutreachWorkspaces","description":"Selectable workspaces. Empty once one is selected - `current_workspace_id` then says which."},"OverrideInput":{"properties":{"date":{"type":"string","title":"Date"},"start_time":{"type":"string","title":"Start Time"},"end_time":{"type":"string","title":"End Time"}},"type":"object","required":["date","start_time","end_time"],"title":"OverrideInput"},"PagesByDomainRequest":{"properties":{"domain":{"type":"string","maxLength":253,"minLength":3,"title":"Domain","description":"Competitor root domain. Subdomains auto-matched."},"limit":{"type":"integer","maximum":500.0,"minimum":1.0,"title":"Limit","default":200},"offset":{"type":"integer","minimum":0.0,"title":"Offset","default":0}},"type":"object","required":["domain"],"title":"PagesByDomainRequest"},"PagesByDomainResponse":{"properties":{"domain":{"type":"string","title":"Domain"},"total_hits":{"type":"integer","title":"Total Hits","default":0},"pages":{"items":{"$ref":"#/components/schemas/IntentPageItem"},"type":"array","title":"Pages","default":[]},"took_ms":{"type":"integer","title":"Took Ms","default":0}},"type":"object","required":["domain"],"title":"PagesByDomainResponse"},"PagesContactsRequest":{"properties":{"urls":{"items":{"type":"string"},"type":"array","maxItems":200,"minItems":1,"title":"Urls"},"limit":{"type":"integer","maximum":500.0,"minimum":1.0,"title":"Limit","default":100},"offset":{"type":"integer","minimum":0.0,"title":"Offset","default":0},"mode":{"type":"string","title":"Mode","default":"quick"}},"type":"object","required":["urls"],"title":"PagesContactsRequest"},"PagesSearchRequest":{"properties":{"query":{"type":"string","maxLength":500,"minLength":1,"title":"Query"},"limit":{"type":"integer","maximum":500.0,"minimum":1.0,"title":"Limit","default":50},"offset":{"type":"integer","minimum":0.0,"title":"Offset","default":0},"semantic_ratio":{"type":"number","maximum":1.0,"minimum":0.0,"title":"Semantic Ratio","description":"0 = text, 1 = semantic, between = hybrid","default":0.0},"filters":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Filters"},"sort":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Sort"},"include_visitors":{"type":"boolean","title":"Include Visitors","default":true}},"type":"object","required":["query"],"title":"PagesSearchRequest"},"PagesSearchResponse":{"properties":{"query":{"type":"string","title":"Query"},"mode":{"type":"string","title":"Mode","default":"text"},"total_hits":{"type":"integer","title":"Total Hits","default":0},"pages":{"items":{"$ref":"#/components/schemas/IntentPageItem"},"type":"array","title":"Pages","default":[]},"took_ms":{"type":"integer","title":"Took Ms","default":0},"warnings":{"items":{"type":"string"},"type":"array","title":"Warnings","description":"Non-fatal problems: visitor counts timed out or failed (pages are then returned unfiltered, visitors=null), every hit was hidden by the has-visitors filter, or the search backend failed."},"visitors_error":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Visitors Error","description":"Why visitor enrichment was skipped (include_visitors=true only)."},"filtered_no_visitors":{"type":"integer","title":"Filtered No Visitors","description":"Hits hidden because they had no visitors in the lookback window (include_visitors=true). total_hits counts them; pages does not.","default":0},"scope_note":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Scope Note","description":"How this search scoped the results, when it differs from a sibling tool (e.g. a bare-domain query matches the apex + www only)."}},"type":"object","required":["query"],"title":"PagesSearchResponse"},"PagesVisitorCountsRequest":{"properties":{"urls":{"items":{"type":"string"},"type":"array","maxItems":15000,"minItems":1,"title":"Urls"}},"type":"object","required":["urls"],"title":"PagesVisitorCountsRequest"},"PagesVisitorsRequest":{"properties":{"url":{"type":"string","maxLength":1024,"minLength":1,"title":"Url","description":"Canonical PAGE_URL, e.g. 'cognism.com/pricing' (no scheme, no www)."},"limit":{"type":"integer","maximum":500.0,"minimum":1.0,"title":"Limit","default":50},"offset":{"type":"integer","minimum":0.0,"title":"Offset","default":0},"mode":{"type":"string","title":"Mode","description":"'quick' (~500ms) or 'full' (~2-3s, all paths).","default":"quick"}},"type":"object","required":["url"],"title":"PagesVisitorsRequest"},"PaginationMeta":{"properties":{"page":{"type":"integer","title":"Page","description":"Current page number (1-indexed)"},"limit":{"type":"integer","title":"Limit","description":"Items per page"},"total":{"type":"integer","title":"Total","description":"Total number of items"},"has_next":{"type":"boolean","title":"Has Next","description":"Whether there are more pages"},"next_cursor":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Next Cursor","description":"Opaque cursor for the next page; null when there are no more items. Pass it back as the `cursor` query param to fetch the following page without computing page numbers."},"total_available":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Total Available","description":"Search endpoints only: how many records really match, when known. Can be larger than `total`, which is capped at the 10,000 results that can be paged. For company search this is a distinct-company estimate. Null when unknown; absent outside search."},"total_is_lower_bound":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Total Is Lower Bound","description":"Search endpoints only: true when more records match than `total` shows (the result set is larger than the 10,000 results that can be paged). Absent outside search."},"notes":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Notes","description":"Search endpoints only: plain-language notes about the result, e.g. that more records match than can be paged, or that a reversed `between` range was put in order."}},"type":"object","required":["page","limit","total","has_next"],"title":"PaginationMeta"},"PasteImportRequest":{"properties":{"headers":{"items":{"type":"string"},"type":"array","maxItems":100,"minItems":1,"title":"Headers"},"rows":{"items":{"items":{},"type":"array"},"type":"array","maxItems":50000,"minItems":1,"title":"Rows"},"raw_source_column_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Raw Source Column Id"}},"type":"object","required":["headers","rows"],"title":"PasteImportRequest","description":"Import a rectangle of values - the paste path, no file involved."},"PatchCompetitorRequest":{"properties":{"tier":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Tier"},"is_active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Active"},"name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Name"},"scan_config":{"anyOf":[{"$ref":"#/components/schemas/ScanConfigDTO"},{"type":"null"}]}},"type":"object","title":"PatchCompetitorRequest"},"PatchDynamicValueRequest":{"properties":{"object_type":{"type":"string","enum":["mashup_contacts","mashup_companies"],"title":"Object Type"},"record_id":{"type":"integer","title":"Record Id","description":"Grid row id."},"column_key":{"type":"string","title":"Column Key","description":"Dynamic column key, e.g. `udo_notes`."},"value":{"anyOf":[{},{"type":"null"}],"title":"Value","description":"New value. Null CLEARS the cell."},"expected_value":{"anyOf":[{},{"type":"null"}],"title":"Expected Value","description":"Refuse the write unless the cell still holds this. Omit to force."}},"type":"object","required":["object_type","record_id","column_key"],"title":"PatchDynamicValueRequest","description":"Write one cell of a user-owned dynamic column.\n\n`expected_value` is an optimistic-concurrency check: send what you believe\nis there and the write is refused if it has moved. Omit it and the write\nwins unconditionally, which on a shared grid means overwriting a\ncolleague's edit without knowing."},"PatchGapRequest":{"properties":{"status":{"type":"string","title":"Status"}},"type":"object","required":["status"],"title":"PatchGapRequest"},"PatchIdeaRequest":{"properties":{"status":{"anyOf":[{"type":"string","enum":["new","saved"]},{"type":"null"}],"title":"Status"},"rating":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Rating"},"scheduled_for":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Scheduled For"}},"type":"object","title":"PatchIdeaRequest","description":"Card actions on a mined idea. Spends nothing.\n\nPARTIAL: an absent field is untouched, a field sent as NULL is CLEARED.\nThose are different instructions and only the second one erases."},"PatchInitiativeRequest":{"properties":{"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id"},"due_date":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"Due Date"},"create_crm_task":{"type":"boolean","title":"Create Crm Task","default":false}},"type":"object","title":"PatchInitiativeRequest","description":"Post-creation edits (F5). Partial-update semantics: a field OMITTED\nfrom the request leaves the stored value unchanged; `owner_id: null`\nexplicitly unassigns (distinguished via `model_fields_set`, not a bare\nNone check)."},"PatchListenerRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"query":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Query"},"target_handle":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Handle"},"filters":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Filters"},"poll_interval_sec":{"anyOf":[{"type":"integer","minimum":60.0},{"type":"null"}],"title":"Poll Interval Sec"},"monthly_credit_cap":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Monthly Credit Cap"},"is_active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Active","description":"False pauses polling without deleting the listener."}},"type":"object","title":"PatchListenerRequest","description":"Partial update. Omitted fields are left alone.\n\nChanging `target_handle` on a `user` listener re-resolves the account\nagainst the platform, which consumes X API quota."},"PatchResponse":{"properties":{"file_path":{"type":"string","title":"File Path"},"action":{"type":"string","title":"Action"},"description":{"type":"string","title":"Description"},"diff":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Diff"},"content":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Content"}},"type":"object","required":["file_path","action","description"],"title":"PatchResponse"},"PatchSetResponse":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"repo_id":{"type":"string","format":"uuid","title":"Repo Id"},"status":{"type":"string","title":"Status"},"patches":{"items":{"$ref":"#/components/schemas/PatchResponse"},"type":"array","title":"Patches"},"applied_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Applied At"},"rolled_back_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Rolled Back At"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"}},"type":"object","required":["id","repo_id","status","patches"],"title":"PatchSetResponse"},"PatchSocialSettingsRequest":{"properties":{"monthly_credit_cap":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Monthly Credit Cap"},"classifier_model":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Classifier Model"},"auto_archive_days":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Auto Archive Days"},"alert_threshold_pct":{"anyOf":[{"type":"integer","maximum":100.0,"minimum":0.0},{"type":"null"}],"title":"Alert Threshold Pct","description":"Alert at this percentage of the cap."},"auto_pause_on_cap":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Auto Pause On Cap","description":"Stop polling when the cap is reached, rather than alerting."},"other_channels_monthly_credit_cap":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Other Channels Monthly Credit Cap","description":"Org-wide monthly credit ceiling across the non-X channels (LinkedIn, Reddit, Instagram, YouTube) together. 0 means no org-wide ceiling; the per-channel caps in `channel_settings` still apply."},"channel_settings":{"anyOf":[{"additionalProperties":{"$ref":"#/components/schemas/ChannelSettingsRule"},"type":"object"},{"type":"null"}],"title":"Channel Settings","description":"Keyed by platform. Keys the app does not recognise are dropped by its own merge - it rebuilds the map from the supported set."},"auto_create_contacts":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Auto Create Contacts"},"contact_capture":{"anyOf":[{"additionalProperties":{"$ref":"#/components/schemas/ContactCaptureRule"},"type":"object"},{"type":"null"}],"title":"Contact Capture"}},"type":"object","title":"PatchSocialSettingsRequest","description":"Org-wide social listening settings. Omitted fields are left alone.\n\nThis is the surface that BOUNDS what the whole feature costs -\n`monthly_credit_cap`, the per-channel caps and `auto_pause_on_cap` between\nthem decide whether an over-eager listener can keep spending."},"PaymentSchedulePreviewRequest":{"properties":{"line_items":{"items":{"$ref":"#/components/schemas/QuoteLineItem"},"type":"array","maxItems":500,"minItems":1,"title":"Line Items"},"contract_start_date":{"type":"string","title":"Contract Start Date","description":"ISO date the contract starts."},"contract_end_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contract End Date"},"contract_months":{"anyOf":[{"type":"number","maximum":120.0,"minimum":0.1},{"type":"null"}],"title":"Contract Months"},"contract_duration_value":{"anyOf":[{"type":"number","maximum":3650.0,"minimum":0.1},{"type":"null"}],"title":"Contract Duration Value"},"contract_duration_unit":{"anyOf":[{"type":"string","enum":["months","weeks","days"]},{"type":"null"}],"title":"Contract Duration Unit"},"tax_amount":{"type":"integer","maximum":1000000000.0,"minimum":0.0,"title":"Tax Amount","default":0}},"type":"object","required":["line_items","contract_start_date"],"title":"PaymentSchedulePreviewRequest","description":"Compute the payment schedule a set of line items WOULD produce.\n\nReads nothing and writes nothing - it is arithmetic over the body, which\nis why it is POST but tiered `read`."},"PerSurveyDTO":{"properties":{"survey_id":{"type":"string","title":"Survey Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"type":{"type":"string","title":"Type"},"delivery_channel":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Delivery Channel"},"nps_score":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Nps Score"},"csat_avg":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Csat Avg"},"promoters":{"type":"integer","title":"Promoters"},"passives":{"type":"integer","title":"Passives"},"detractors":{"type":"integer","title":"Detractors"},"total_respondents":{"type":"integer","title":"Total Respondents"},"is_active":{"type":"boolean","title":"Is Active","default":true},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"audience_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience Ref"},"audience_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience Name"},"audience_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Audience Count"},"sent_count":{"type":"integer","title":"Sent Count","default":0},"cadence_kind":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Cadence Kind"},"cadence_days":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Cadence Days"},"cadence_label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Cadence Label"},"trend":{"items":{"$ref":"#/components/schemas/TrendBarDTO"},"type":"array","title":"Trend","default":[]}},"type":"object","required":["survey_id","type","promoters","passives","detractors","total_respondents"],"title":"PerSurveyDTO"},"PersonLookupRequest":{"properties":{"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email","description":"Work email address"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url","description":"LinkedIn profile URL"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name","description":"First name (requires last_name + company_domain)"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name","description":"Last name (requires first_name + company_domain)"},"company_domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Domain","description":"Company domain (requires first_name + last_name)"}},"type":"object","title":"PersonLookupRequest"},"PersonaFillFromDocRequest":{"properties":{"website_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Website Url","description":"Stored on any persona row this creates. Optional: the committees view is org-wide and does not filter on it."}},"type":"object","title":"PersonaFillFromDocRequest"},"PersonaGenerateRequest":{"properties":{"website_url":{"type":"string","title":"Website Url","description":"The website the personas are researched from."},"save_to_database":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Save To Database","description":"Persist the generated personas. False returns a preview only.","default":true}},"type":"object","required":["website_url"],"title":"PersonaGenerateRequest"},"PersonaLensRequest":{"properties":{"persona":{"$ref":"#/components/schemas/CampaignSetPersona"}},"type":"object","required":["persona"],"title":"PersonaLensRequest","description":"Read the ad through a persona's eyes. SPENDS CREDIT.\n\nRead-only against the creative - it returns a critique and changes\nnothing - but a model still runs, so it still costs."},"PersonaRecommendationRequest":{"properties":{"organization_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Organization Id","description":"Ignored. The organisation is the API key's own."},"website_url":{"type":"string","title":"Website Url"}},"type":"object","required":["website_url"],"title":"PersonaRecommendationRequest","description":"Recommend target personas from the company's own data. SPENDS CREDIT.\n\n`organization_id` is IGNORED - the org always comes from the key. It is\nmirrored because the app's model carries it, and dropping a field a caller\nsends would be a silent 422 on a body Studio itself produces."},"PersonalContactChoiceRequest":{"properties":{"fact_ids":{"items":{"type":"string"},"type":"array","maxItems":500,"title":"Fact Ids","description":"The people (wiki facts) this choice applies to."},"connection_revisions":{"additionalProperties":{"type":"integer","minimum":1.0},"propertyNames":{"maxLength":36,"minLength":36},"type":"object","maxProperties":100,"title":"Connection Revisions","description":"Per-connection revision tokens, keyed by connection id (UUID)."},"mode":{"type":"string","enum":["default","private","shared"],"title":"Mode","description":"`private` keeps these people to yourself, `shared` offers them to the org's CRM, `default` follows the mailbox-level setting."},"expected_revision":{"type":"integer","minimum":0.0,"title":"Expected Revision","description":"Concurrency token from the sharing GET."}},"type":"object","required":["mode","expected_revision"],"title":"PersonalContactChoiceRequest","description":"Mirror of `PersonalContactChoiceRequest`."},"PersonalContactIdentityRequest":{"properties":{"fact_ids":{"items":{"type":"string","maxLength":255,"minLength":1},"type":"array","maxItems":1000,"minItems":1,"title":"Fact Ids","description":"The facts being re-attributed, all to the same person."},"contact_id":{"anyOf":[{"type":"integer","maximum":9.223372036854776e+18,"exclusiveMinimum":0.0},{"type":"null"}],"title":"Contact Id","description":"Who they are really about. NULL DETACHES them from whoever they are attributed to now, rather than being ignored - it is how you say 'this is not about anyone in the CRM'."},"expected_version":{"type":"integer","minimum":0.0,"title":"Expected Version","description":"Optimistic-concurrency token for the relationship record."}},"type":"object","required":["fact_ids","expected_version"],"title":"PersonalContactIdentityRequest","description":"Mirror of `PersonalContactIdentityRequest`."},"PersonalContactMatchRequest":{"properties":{"contact_id":{"type":"integer","maximum":9.223372036854776e+18,"exclusiveMinimum":0.0,"title":"Contact Id","description":"The CRM contact this contribution is actually about."},"expected_revision":{"type":"integer","minimum":1.0,"title":"Expected Revision"},"expected_canonical_revision":{"type":"string","maxLength":64,"minLength":64,"title":"Expected Canonical Revision"}},"type":"object","required":["contact_id","expected_revision","expected_canonical_revision"],"title":"PersonalContactMatchRequest","description":"Mirror of `PersonalContactMatchRequest`."},"PersonalContactReviewRequest":{"properties":{"expected_revision":{"type":"integer","minimum":1.0,"title":"Expected Revision","description":"The contribution's revision."},"expected_canonical_revision":{"type":"string","maxLength":64,"minLength":64,"title":"Expected Canonical Revision","description":"Digest of the CANONICAL contact record as you read it. Two tokens are required because two records are in play: the contribution and the contact it would change. Either moving means the decision was made against something that no longer holds."},"field":{"type":"string","enum":["CONTACT_FIRST_NAME","CONTACT_LAST_NAME","CONTACT_JOB_TITLE"],"title":"Field","description":"Which field is being decided."},"choice":{"type":"string","enum":["keep_current","use_proposed"],"title":"Choice","description":"`keep_current` - the CRM record wins. `use_proposed` - the contributed value wins and overwrites it."}},"type":"object","required":["expected_revision","expected_canonical_revision","field","choice"],"title":"PersonalContactReviewRequest","description":"Mirror of `PersonalContactReviewRequest`."},"PersonalContactSharingRequest":{"properties":{"enabled":{"type":"boolean","title":"Enabled","description":"Whether what this mailbox knows about a contact is contributed to the organisation's shared CRM record. Explicit rather than a toggle, so a retry is idempotent instead of switching it back."},"expected_revision":{"type":"integer","minimum":0.0,"title":"Expected Revision","description":"REQUIRED optimistic-concurrency token. Sharing settings decide whether one person's private contact knowledge becomes org-wide, so there is no unconditional write: a blind one could re-enable sharing somebody had just turned off."}},"type":"object","required":["enabled","expected_revision"],"title":"PersonalContactSharingRequest","description":"Mirror of `PersonalContactSharingRequest`."},"PersonalDriveFolderChoice":{"properties":{"id":{"type":"string","pattern":"^[A-Za-z0-9_-]{10,200}$","title":"Id","description":"Drive folder id, as returned by `GET /copilot/personal-wiki/drive`."},"auto_sync":{"type":"boolean","title":"Auto Sync","description":"Keep reading new documents added to this folder later, not just today's.","default":false}},"type":"object","required":["id"],"title":"PersonalDriveFolderChoice","description":"Mirror of `PersonalDriveFolderChoice`."},"PersonalDriveSelectionRequest":{"properties":{"mailbox_id":{"type":"integer","exclusiveMinimum":0.0,"title":"Mailbox Id","description":"Integer `mailboxes.id` of the connected Google account."},"document_ids":{"items":{"type":"string"},"type":"array","maxItems":20,"title":"Document Ids","description":"Individual Drive documents to read."},"folders":{"items":{"$ref":"#/components/schemas/PersonalDriveFolderChoice"},"type":"array","maxItems":10,"title":"Folders","description":"Whole folders to read."},"revision":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Revision","description":"The sources' `updated_at` from `GET /copilot/personal-wiki/sources`. A mismatch is a 409: someone else changed the selection since you read it."},"preview_fingerprint":{"anyOf":[{"type":"string","pattern":"^[a-f0-9]{64}$"},{"type":"null"}],"title":"Preview Fingerprint","description":"The `fingerprint` from the preview call. When sent, the save is refused (409) if the selection no longer resolves to what you previewed."}},"type":"object","required":["mailbox_id"],"title":"PersonalDriveSelectionRequest","description":"Mirror of `PersonalDriveSelectionRequest`."},"PersonalLinkedInImportRequest":{"properties":{"expected_revision":{"type":"integer","minimum":0.0,"title":"Expected Revision","description":"The `revision` from the GET. A stale value is a 409."},"keep_updated":{"type":"boolean","title":"Keep Updated","description":"Re-import the connection list on a schedule.","default":false},"share":{"type":"boolean","title":"Share","description":"Offer what is learned from these connections to the shared CRM (reviewed first).","default":false},"start":{"type":"boolean","title":"Start","description":"Start an import now, rather than only saving the settings.","default":false}},"type":"object","required":["expected_revision"],"title":"PersonalLinkedInImportRequest","description":"Mirror of `PersonalLinkedInImportRequest`."},"PersonalWikiFactActionRequest":{"properties":{"fact_id":{"type":"string","maxLength":255,"minLength":1,"title":"Fact Id","description":"The fact."},"reason":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Reason","description":"Why. Optional, and worth sending on a forget: it is the only record of why something was removed from what the Copilot knows."}},"type":"object","required":["fact_id"],"title":"PersonalWikiFactActionRequest","description":"Mirror of `PersonalWikiFactActionRequest` - used by confirm and forget."},"PersonalWikiFactCorrectionRequest":{"properties":{"fact_id":{"type":"string","maxLength":255,"minLength":1,"title":"Fact Id"},"reason":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Reason"},"text":{"type":"string","maxLength":10000,"minLength":1,"title":"Text","description":"What is actually true. Replaces the fact's text."},"action_state":{"anyOf":[{"type":"string","enum":["open","in_progress","blocked","completed","cancelled","informational"]},{"type":"null"}],"title":"Action State","description":"For a fact the Copilot is tracking as a TO-DO rather than as a statement, move it to this state at the same time. Omit it for an ordinary correction."}},"type":"object","required":["fact_id","text"],"title":"PersonalWikiFactCorrectionRequest","description":"Mirror of `PersonalWikiFactCorrectionRequest`.\n\nThe app declares it as a SUBCLASS of the action request and restates the\ninherited fields. Flattened here because a generated SDK renders\ninheritance as a separate schema for no benefit, and the parity test\ncompares the RESOLVED field set, which is identical."},"PersonalWikiItemEditRequest":{"properties":{"document_id":{"type":"string","maxLength":100,"minLength":1,"title":"Document Id"},"expected_revision":{"type":"string","maxLength":64,"minLength":64,"title":"Expected Revision","description":"REQUIRED optimistic-concurrency token - a 64-character digest of the document you read. There is no unconditional write here, on purpose: the wiki is edited by the Copilot as well as by people, so a blind write would silently discard something it had just learned."},"values":{"additionalProperties":true,"type":"object","title":"Values","description":"Field-by-field replacement for this item. Open-shaped because the item schema is per-section and defined by the wiki template."}},"type":"object","required":["document_id","expected_revision","values"],"title":"PersonalWikiItemEditRequest","description":"Mirror of `PersonalWikiItemEditRequest`."},"PersonalWikiSourcesUpdateRequest":{"properties":{"primary_mailbox_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Primary Mailbox Id","description":"The mailbox the wiki draws its email signal from."},"additional_mailbox_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array","maxItems":20},{"type":"null"}],"title":"Additional Mailbox Ids","description":"Further mailboxes to read."},"email_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Email Enabled","description":"Whether the Copilot reads your email to build the wiki. Turning this off stops new facts arriving from email; it does not remove what it already learned - use `POST /copilot/personal-wiki/forget` for that."},"calendar_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Calendar Enabled","description":"Read your calendar."},"docs_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Docs Enabled","description":"Read the named documents."},"document_ids":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":20},{"type":"null"}],"title":"Document Ids","description":"Which documents, when `docs_enabled`."},"work_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Work Enabled","description":"Read your Work activity."}},"type":"object","title":"PersonalWikiSourcesUpdateRequest","description":"Mirror of `PersonalWikiSourcesUpdateRequest`.\n\nPARTIAL: the handler applies `exclude_unset`, so an omitted field is left\nalone and an explicit value changes it. Sending `email_enabled: false` is\nnot the same instruction as omitting it."},"PersonalWikiUpdateRequest":{"properties":{"content":{"type":"string","maxLength":100000,"title":"Content","description":"The WHOLE wiki document. Replaces what is there."},"title":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Title"}},"type":"object","required":["content"],"title":"PersonalWikiUpdateRequest","description":"Mirror of `PersonalWikiUpdateRequest`."},"PhoneA2pStatusPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"PhoneA2pStatusPayload","description":"The org's A2P brand and campaign registration state."},"PhoneDirectoryEntryCreate":{"properties":{"user_email":{"type":"string","title":"User Email"},"user_name":{"type":"string","title":"User Name"},"extension":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Extension"},"phone_number":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone Number"},"department":{"type":"string","title":"Department"},"availability":{"type":"string","title":"Availability","default":"available"},"is_active":{"type":"boolean","title":"Is Active","default":true}},"type":"object","required":["user_email","user_name","department"],"title":"PhoneDirectoryEntryCreate","description":"A colleague the receptionist and the in-call transfer picker can reach.\n\n`extension` and `phone_number` are both optional: the number a transfer\nactually dials is resolved from the work-number inventory first, and the\nstored `phone_number` is only the hand-entered override."},"PhoneDirectoryEntryUpdate":{"properties":{"user_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Name"},"extension":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Extension"},"phone_number":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone Number"},"department":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Department"},"availability":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Availability"},"is_active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Active"}},"type":"object","title":"PhoneDirectoryEntryUpdate"},"PhoneNumberPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"PhoneNumberPayload","description":"An open envelope for a purchase result, a release, or an A2P job.\n\nOpen on purpose. A purchase returns the stored row (whose capability and\nprovider-metadata keys differ per provider), a workflow start returns a\n`workflow_id`, and the A2P reconcile returns per-number outcomes that grow\nas carriers add statuses. Pinning it would silently drop whatever the\nprovider reported that this contract had not caught up on."},"PhoneNumberSearchPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"PhoneNumberSearchPayload","description":"Numbers available to buy, under `items`."},"PhoneNumberSearchRequest":{"properties":{"provider":{"type":"string","title":"Provider","description":"The carrier to search - the same values `POST /phone-numbers/purchase` takes."},"country":{"type":"string","title":"Country","description":"ISO country code.","default":"US"},"area_code":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Area Code"},"number_type":{"type":"string","title":"Number Type","description":"`local` or `toll_free`.","default":"local"},"pattern":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Pattern","description":"Digits or a phrase the number must contain."},"match":{"type":"string","title":"Match","description":"Where `pattern` must appear: `first`, `anywhere` or `last`.","default":"first"},"locality":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Locality","description":"City. Use this or `pattern`, not both."}},"type":"object","required":["provider"],"title":"PhoneNumberSearchRequest"},"PipelineByChannelPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"PipelineByChannelPayload","description":"Pipeline by first, last or any touch channel (`rows`, `by_rep`, `total`)."},"PipelineBySourceDealsPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"PipelineBySourceDealsPayload","description":"The deals behind a cell of the pipeline-by-source report (`total`, `deals`)."},"PipelineBySourcePayload":{"properties":{},"additionalProperties":true,"type":"object","title":"PipelineBySourcePayload","description":"Pipeline by source: per-channel, monthly, meeting-path, assisted and per-rep figures for two periods."},"PipelineCreateRequest":{"properties":{"name":{"type":"string","title":"Name","default":"Sales Pipeline"},"target":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target"},"blank":{"type":"boolean","title":"Blank","default":false}},"type":"object","title":"PipelineCreateRequest"},"PipelineExpectedField":{"properties":{"name":{"type":"string","maxLength":255,"minLength":1,"title":"Name"},"display_name":{"type":"string","maxLength":255,"title":"Display Name","default":""},"data_type":{"type":"string","enum":["text","number","boolean","json"],"title":"Data Type","default":"text"},"locked":{"type":"boolean","title":"Locked","default":false}},"type":"object","required":["name"],"title":"PipelineExpectedField"},"PipelineResponse":{"properties":{"id":{"type":"string","title":"Id"},"name":{"type":"string","title":"Name"},"is_default":{"type":"boolean","title":"Is Default","default":false},"stages":{"items":{"$ref":"#/components/schemas/PipelineStageResponse"},"type":"array","title":"Stages","default":[]}},"type":"object","required":["id","name"],"title":"PipelineResponse"},"PipelineStageResponse":{"properties":{"id":{"type":"string","title":"Id"},"name":{"type":"string","title":"Name"},"probability":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Probability"},"position":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Position"},"stage_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage Type"},"color":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Color"},"required_elements":{"items":{"type":"string"},"type":"array","title":"Required Elements"},"recommended_elements":{"items":{"type":"string"},"type":"array","title":"Recommended Elements"},"channel_scripts":{"additionalProperties":{"type":"string"},"type":"object","title":"Channel Scripts"}},"type":"object","required":["id","name"],"title":"PipelineStageResponse"},"PipelineStartConfig":{"properties":{"type":{"type":"string","enum":["email_pdf","webhook","scraper_bot","ingest"],"title":"Type"},"source_types":{"items":{"type":"string"},"type":"array","title":"Source Types"},"expected_fields":{"items":{"$ref":"#/components/schemas/PipelineExpectedField"},"type":"array","title":"Expected Fields"}},"type":"object","required":["type"],"title":"PipelineStartConfig","description":"What starts the pipeline."},"PipelineUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"target":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target"},"set_default":{"type":"boolean","title":"Set Default","default":false}},"type":"object","title":"PipelineUpdateRequest"},"PlanMediaEntry":{"properties":{"role":{"type":"string","maxLength":80,"minLength":1,"title":"Role"},"context":{"type":"string","maxLength":200,"minLength":1,"title":"Context"},"asset_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Asset Id"},"asset_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Asset Url"},"asset_type":{"type":"string","enum":["image","video"],"title":"Asset Type"},"position_hint":{"type":"string","enum":["hero","body","any"],"title":"Position Hint","default":"any"},"locked":{"type":"boolean","title":"Locked","default":false}},"type":"object","required":["role","context","asset_type"],"title":"PlanMediaEntry","description":"One media slot inside a plan section.\n\n``locked=True`` marks items the user explicitly attached (no swap\naffordance in the UI). AI-picked items default to ``locked=False``\nand can be swapped before approval."},"PlanSection":{"properties":{"name":{"type":"string","maxLength":80,"minLength":1,"title":"Name"},"purpose":{"type":"string","maxLength":200,"title":"Purpose"},"media":{"items":{"$ref":"#/components/schemas/PlanMediaEntry"},"type":"array","maxItems":4,"title":"Media"}},"type":"object","required":["name","purpose"],"title":"PlanSection","description":"One section of the landing-page plan."},"PlanTerms":{"properties":{"name":{"type":"string","maxLength":120,"minLength":1,"title":"Name"},"currency":{"type":"string","const":"USD","title":"Currency","default":"USD"},"effective_from":{"type":"string","format":"date","title":"Effective From"},"effective_until":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"Effective Until"},"quality_policy":{"type":"string","maxLength":2000,"title":"Quality Policy","default":""},"eligibility_policy":{"type":"string","maxLength":4000,"minLength":1,"title":"Eligibility Policy"},"rules":{"items":{"$ref":"#/components/schemas/Rule"},"type":"array","maxItems":100,"minItems":1,"title":"Rules"}},"additionalProperties":false,"type":"object","required":["name","effective_from","eligibility_policy","rules"],"title":"PlanTerms"},"Preview":{"properties":{"terms":{"$ref":"#/components/schemas/PlanTerms"},"collection":{"$ref":"#/components/schemas/Collection"}},"additionalProperties":false,"type":"object","required":["terms","collection"],"title":"Preview"},"PreviewChannelItem":{"properties":{"id":{"type":"string","title":"Id"},"channel_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Channel Id"},"channel_value":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Channel Value"},"channel_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Channel Type"}},"type":"object","required":["id"],"title":"PreviewChannelItem"},"PreviewCostRequest":{"properties":{"platform":{"type":"string","enum":["x","linkedin","reddit","instagram","youtube"],"title":"Platform","default":"x"},"listener_type":{"type":"string","enum":["brand","competitor","keyword","engagement","user"],"title":"Listener Type"},"query":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Query"},"target_handle":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Handle"},"poll_interval_sec":{"type":"integer","minimum":60.0,"title":"Poll Interval Sec","description":"The interval to cost. Shorter intervals cost more.","default":600}},"type":"object","required":["listener_type"],"title":"PreviewCostRequest","description":"Ask what a listener WOULD cost. Charges nothing."},"PreviewDetectionRuleRequest":{"properties":{"rule_name":{"type":"string","title":"Rule Name","description":"Name for the rule being previewed."},"template":{"type":"string","title":"Template","description":"Platform rule template the rule is built from."},"entity_type":{"type":"string","enum":["contact","company","deal"],"title":"Entity Type","description":"Object the rule matches on."},"field":{"type":"string","title":"Field","description":"Column the rule compares."},"match_mode":{"type":"string","enum":["exact","normalized","fuzzy_levenshtein","domain_match","phone_e164","linkedin_handle"],"title":"Match Mode","description":"How two values are considered equal."},"score":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Score","description":"Override the platform default score for this rule."},"confidence_bucket":{"anyOf":[{"type":"string","enum":["high","medium","low"]},{"type":"null"}],"title":"Confidence Bucket","description":"Override the default confidence bucket."}},"type":"object","required":["rule_name","template","entity_type","field","match_mode"],"title":"PreviewDetectionRuleRequest","description":"Dry-run a duplicate-detection rule. Writes nothing.\n\nReturns how many pairs the rule would match plus a small sample, which is\nthe only way to size a rule before auto-merge starts acting on it."},"PreviewKeywordUrlsRequest":{"properties":{"keyword":{"type":"string","minLength":1,"title":"Keyword","description":"The keyword to preview."},"search_filters":{"$ref":"#/components/schemas/KeywordFilters","description":"Filters to preview it with."}},"type":"object","required":["keyword"],"title":"PreviewKeywordUrlsRequest","description":"What a keyword WOULD match, without creating it."},"PreviewRollup":{"properties":{"node_path":{"type":"string","title":"Node Path","description":"Where the rollup sits in the expression: `$` is the root, `$.left`, `$.args[1]`, `$.then_branch`."},"matched_count":{"type":"integer","title":"Matched Count","description":"Linked records the rollup counted for the preview record (the ones its filters keep)."}},"type":"object","required":["node_path","matched_count"],"title":"PreviewRollup","description":"How many linked records one rollup of a previewed expression counted."},"PreviewRoutingRequest":{"properties":{"source_list_id":{"type":"integer","title":"Source List Id"},"conditions":{"items":{"$ref":"#/components/schemas/ConditionDto"},"type":"array","title":"Conditions"}},"type":"object","required":["source_list_id"],"title":"PreviewRoutingRequest","description":"Count what a routing rule WOULD move, without moving anything."},"PreviewStepItem":{"properties":{"id":{"type":"string","title":"Id"},"step_order":{"type":"integer","title":"Step Order"},"step_type":{"type":"string","title":"Step Type"},"input_type":{"type":"string","title":"Input Type"},"time_interval":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Time Interval"},"step_data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Step Data"},"rendered":{"anyOf":[{"$ref":"#/components/schemas/RenderedStepContent"},{"type":"null"}],"description":"Spintax-resolved view of this step's copy. Populated for template steps that carry subject/body. Null for ON_DEMAND steps, whose copy is written by the AI at send time rather than stored here."}},"type":"object","required":["id","step_order","step_type","input_type"],"title":"PreviewStepItem"},"PrewarmVoicemailsRequest":{"properties":{"agent_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent Id"},"contacts":{"items":{"$ref":"#/components/schemas/DialContact"},"type":"array","maxItems":20,"minItems":1,"title":"Contacts"}},"type":"object","required":["contacts"],"title":"PrewarmVoicemailsRequest","description":"Mirrors `DialerPrewarmRequest` minus `org_id`.\n\nSYNTHESISES voicemail audio ahead of time. Contacts nobody, but it is real\ntext-to-speech work per contact, which is why it is not a plain write.\nVoice caps the batch at 20 and that cap is mirrored here so an oversized\nbatch is a 422 from this API rather than a round-trip."},"ProcessListCreate":{"properties":{"api_slug":{"type":"string","maxLength":93,"minLength":1,"pattern":"^[a-z][a-z0-9_]*$","title":"Api Slug"},"singular_noun":{"type":"string","maxLength":100,"minLength":1,"title":"Singular Noun"},"plural_noun":{"type":"string","maxLength":100,"minLength":1,"title":"Plural Noun"},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description"},"icon":{"anyOf":[{"type":"string","enum":["box","briefcase","building","calendar","flag","folder","globe","heart","layers","package","target","users"]},{"type":"null"}],"title":"Icon"},"parent":{"$ref":"#/components/schemas/RelationshipTarget"},"parent_label":{"type":"string","maxLength":100,"minLength":1,"title":"Parent Label"},"entries_label":{"type":"string","maxLength":100,"minLength":1,"title":"Entries Label"}},"additionalProperties":false,"type":"object","required":["api_slug","singular_noun","plural_noun","parent","parent_label","entries_label"],"title":"ProcessListCreate"},"ProcessListEntryCreate":{"properties":{"values":{"additionalProperties":true,"type":"object","title":"Values"},"parent_record_id":{"type":"string","maxLength":255,"minLength":1,"title":"Parent Record Id"},"expected_parent_revision":{"anyOf":[{"type":"integer","exclusiveMinimum":0.0},{"type":"null"}],"title":"Expected Parent Revision"},"idempotency_key":{"anyOf":[{"type":"string","maxLength":255,"minLength":1},{"type":"null"}],"title":"Idempotency Key"}},"additionalProperties":false,"type":"object","required":["parent_record_id"],"title":"ProcessListEntryCreate","description":"Create one entry (a record of the list's object) and link it to its parent, atomically.\n\nThe parent KIND is not repeated: the list's own relationship definition fixes it."},"ProcessListEntryResponse":{"properties":{"record":{"$ref":"#/components/schemas/RecordResponse"},"relationship_id":{"type":"string","format":"uuid","title":"Relationship Id"},"parent":{"$ref":"#/components/schemas/ProcessListParentSummary"},"replayed":{"type":"boolean","title":"Replayed","default":false}},"type":"object","required":["record","relationship_id","parent"],"title":"ProcessListEntryResponse"},"ProcessListListResponse":{"properties":{"process_lists":{"items":{"$ref":"#/components/schemas/ProcessListResponse"},"type":"array","title":"Process Lists"},"total":{"type":"integer","title":"Total"}},"type":"object","required":["process_lists","total"],"title":"ProcessListListResponse"},"ProcessListParentSummary":{"properties":{"kind":{"type":"string","enum":["custom","contacts","companies","deals"],"title":"Kind"},"record_id":{"type":"string","title":"Record Id"},"object_slug":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Object Slug"},"label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Label"},"revision":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Revision"}},"type":"object","required":["kind","record_id"],"title":"ProcessListParentSummary"},"ProcessListResponse":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"api_slug":{"type":"string","title":"Api Slug"},"singular_noun":{"type":"string","title":"Singular Noun"},"plural_noun":{"type":"string","title":"Plural Noun"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"icon":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Icon"},"display_attribute_slug":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display Attribute Slug"},"is_archived":{"type":"boolean","title":"Is Archived"},"created_at":{"type":"string","format":"date-time","title":"Created At"},"updated_at":{"type":"string","format":"date-time","title":"Updated At"},"parent_relationship_definition_id":{"type":"string","format":"uuid","title":"Parent Relationship Definition Id"},"parent_kind":{"type":"string","enum":["custom","contacts","companies","deals"],"title":"Parent Kind"},"parent_object_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Parent Object Id"},"parent_object_slug":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Parent Object Slug"},"parent_label":{"type":"string","title":"Parent Label"},"entries_label":{"type":"string","title":"Entries Label"}},"type":"object","required":["id","api_slug","singular_noun","plural_noun","is_archived","created_at","updated_at","parent_relationship_definition_id","parent_kind","parent_label","entries_label"],"title":"ProcessListResponse"},"ProcessListUpdate":{"properties":{"singular_noun":{"anyOf":[{"type":"string","maxLength":100,"minLength":1},{"type":"null"}],"title":"Singular Noun"},"plural_noun":{"anyOf":[{"type":"string","maxLength":100,"minLength":1},{"type":"null"}],"title":"Plural Noun"},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description"},"icon":{"anyOf":[{"type":"string","enum":["box","briefcase","building","calendar","flag","folder","globe","heart","layers","package","target","users"]},{"type":"null"}],"title":"Icon"},"is_archived":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Archived"},"display_attribute_slug":{"anyOf":[{"type":"string","maxLength":100,"minLength":1,"pattern":"^[a-z][a-z0-9_]*$"},{"type":"null"}],"title":"Display Attribute Slug"}},"additionalProperties":false,"type":"object","title":"ProcessListUpdate","description":"Rename, describe or archive a list. The parent binding is never accepted here."},"ProductSettingsUpdateRequest":{"properties":{"friendly_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Friendly Name"},"friendly_description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Friendly Description"},"quotable":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Quotable"},"category":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Category"},"sort_order":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Sort Order"}},"type":"object","title":"ProductSettingsUpdateRequest","description":"How a Stripe product appears in the quote builder. Omitted fields are unchanged."},"ProfileDealAutomationsUpdateRequest":{"properties":{"sync_interval_minutes":{"anyOf":[{"type":"integer","enum":[10,30,60,180,360,1440]},{"type":"null"}],"title":"Sync Interval Minutes","description":"How often the calendar is pulled, in minutes."},"pipelines":{"anyOf":[{"additionalProperties":{"$ref":"#/components/schemas/ProfilePipelineAutomationBlock"},"type":"object"},{"type":"null"}],"title":"Pipelines","description":"Rules per pipeline id. Only the pipelines sent are changed; the others, and other people's rules, are never touched."}},"type":"object","title":"ProfileDealAutomationsUpdateRequest","description":"Mirrors `user_profile.DealAutomationsUpdateRequest`.\n\n`sync_interval_minutes` is closed to `SYNC_INTERVAL_CHOICES`. The app's own\nvalidator raises a ValueError for anything else, which - raised while the\nproxy builds the app model - would escape as a 500."},"ProfileFieldsRequest":{"properties":{"website_url":{"type":"string","title":"Website Url","description":"The org's website - the profile's key."},"fields":{"additionalProperties":true,"type":"object","title":"Fields","description":"Which profile fields to generate, and their seeds."}},"type":"object","required":["website_url","fields"],"title":"ProfileFieldsRequest","description":"Mirrors `company_profile.SaveProfileRequest`."},"ProfileNotificationPreferenceUpdateRequest":{"properties":{"event_type":{"type":"string","title":"Event Type","description":"The event to configure, as listed by `GET /profile/notification-preferences`. An unknown one is refused with the valid list."},"enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Enabled"},"copilot_proactive":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Copilot Proactive"},"copilot_bridge":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Copilot Bridge"},"bridge_whatsapp":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Bridge Whatsapp"},"bridge_slack":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Bridge Slack"},"bridge_roam":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Bridge Roam"},"bridge_imessage":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Bridge Imessage"},"bridge_email":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Bridge Email"},"routing":{"anyOf":[{"type":"string","enum":["conversation","notify_only","off"]},{"type":"null"}],"title":"Routing"},"urgency":{"anyOf":[{"type":"string","enum":["interrupt_now","fold_into_brief"]},{"type":"null"}],"title":"Urgency"},"hot_override":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Hot Override"}},"type":"object","required":["event_type"],"title":"ProfileNotificationPreferenceUpdateRequest","description":"Mirrors `user_profile.NotificationPreferenceUpdateRequest`.\n\nUpdates ONE event type per call - `event_type` is required and names it.\n`routing` and `urgency` are closed to the app's `VALID_ROUTING` /\n`VALID_URGENCY` vocabulary (a parity test pins them)."},"ProfilePicturesRequest":{"properties":{"linkedin_urls":{"items":{"type":"string"},"type":"array","maxItems":200,"title":"Linkedin Urls","description":"LinkedIn profile URLs (deduplicated, max 200)."}},"type":"object","title":"ProfilePicturesRequest","description":"Resolve profile photos for a batch of LinkedIn URLs.\n\nReturns an entry only for contacts that have an allow-listed https photo,\nso a missing key means \"no photo\", not \"lookup failed\"."},"ProfilePipelineAutomationBlock":{"properties":{"enabled":{"type":"boolean","title":"Enabled","default":false},"dry_run":{"type":"boolean","title":"Dry Run","default":false},"title_keywords":{"items":{"type":"string"},"type":"array","maxItems":10,"title":"Title Keywords","description":"Meeting-title keywords that count. At most 10; each is trimmed to 100 characters and duplicates are dropped case-insensitively."},"generate_scope_of_work":{"type":"boolean","title":"Generate Scope Of Work","default":false},"auto_draft_quote":{"type":"boolean","title":"Auto Draft Quote","default":false},"auto_advance_deal_on_quote_send":{"type":"boolean","title":"Auto Advance Deal On Quote Send","default":false},"auto_close_deal_on_acceptance":{"type":"boolean","title":"Auto Close Deal On Acceptance","default":false}},"type":"object","title":"ProfilePipelineAutomationBlock","description":"Mirrors `user_profile.PipelineAutomationBlock`.\n\n`dry_run` is the safety switch: with it on, the automation reports what it\nWOULD do and creates nothing."},"ProfilePreferencesUpdateRequest":{"properties":{"notifications_email":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Notifications Email"},"notifications_slack":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Notifications Slack"},"notifications_in_app":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Notifications In App"},"default_view":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Default View"},"theme":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Theme"},"timezone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Timezone"},"locale":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Locale"},"mcp_default_client":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mcp Default Client"},"mcp_tool_group":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mcp Tool Group","description":"An id from `GET /profile/mcp/tools` (a `groups[].value` or a `toolboxes[].id`). Anything else is a 422 that lists the valid ids."},"mcp_widgets_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Mcp Widgets Enabled"},"whatsapp_number":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Whatsapp Number"}},"type":"object","title":"ProfilePreferencesUpdateRequest","description":"Mirrors `user_profile.PreferencesUpdateRequest`.\n\nEvery field optional; omitted fields are left alone."},"ProfileWebsiteRequest":{"properties":{"website_url":{"type":"string","title":"Website Url","description":"Website the profile was built from. Matched on its canonical domain."}},"type":"object","required":["website_url"],"title":"ProfileWebsiteRequest","description":"Names the company profile to act on, by the website it was built from.\n\nMirrors `campaign_builder.routers.company_profile.ApproveProfileRequest`,\nwhich is the same single field. The reindex route reads the same value as\na QUERY parameter on a POST in the app; it is a body here because a POST\nthat carries its only input in the URL is the kind of asymmetry a client\nlibrary gets wrong once and then works around forever."},"ProgrammaticBulkPageActionRequest":{"properties":{"action":{"type":"string","enum":["mark_ready_to_deploy_selected","unpublish_selected","mark_for_regeneration_selected","deploy_pending_changes","republish_all","rollback_publish","queue_search_console","delete_selected","export_urls","publish_selected","regenerate_selected"],"title":"Action"},"page_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Page Ids"}},"type":"object","required":["action"],"title":"ProgrammaticBulkPageActionRequest","description":"A lifecycle action on many generated pages (or all, for the deploy actions)."},"ProgrammaticPageActionRequest":{"properties":{"action":{"type":"string","enum":["mark_ready_to_deploy","unpublish","mark_for_regeneration","override","reset_override","publish","regenerate"],"title":"Action"},"html_output":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Html Output"},"manual_override":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Manual Override"}},"type":"object","required":["action"],"title":"ProgrammaticPageActionRequest","description":"A lifecycle action on one generated page. `publish` / `regenerate` are aliases."},"ProgrammaticPreviewRequest":{"properties":{"contact_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Contact Id"}},"type":"object","title":"ProgrammaticPreviewRequest","description":"Render one page. Omit `contact_id` for the source's first row."},"ProgrammaticSitemapImportRequest":{"properties":{"sitemap_url":{"type":"string","title":"Sitemap Url"},"source_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Name"},"max_urls":{"type":"integer","title":"Max Urls","default":250},"fetch_pages":{"type":"boolean","title":"Fetch Pages","default":false}},"type":"object","required":["sitemap_url"],"title":"ProgrammaticSitemapImportRequest","description":"Import an existing sitemap as the campaign's data source."},"ProgrammaticWorkspaceUpdateRequest":{"properties":{"data_source_type":{"anyOf":[{"type":"string","enum":["list","workbench","csv","seo_import"]},{"type":"null"}],"title":"Data Source Type"},"data_source_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Data Source Id"},"data_source_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Data Source Name"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"slug_template":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slug Template"},"variable_config":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Variable Config"},"settings":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Settings"}},"type":"object","title":"ProgrammaticWorkspaceUpdateRequest","description":"Workspace settings: source, templating, SEO, linking, deployment, regeneration."},"PromoteDeploymentRequest":{"properties":{"image_digest":{"type":"string","maxLength":128,"minLength":7,"title":"Image Digest","description":"The built image digest being promoted. Recorded so a rollback targets an artifact rather than a rebuild."}},"type":"object","required":["image_digest"],"title":"PromoteDeploymentRequest"},"PromoteMemoryRequest":{"properties":{"subject_type":{"type":"string","title":"Subject Type","description":"organization | user | campaign | company | contact."},"subject_id":{"type":"string","title":"Subject Id","description":"Which one."},"days_back":{"type":"integer","title":"Days Back","description":"How far back through the daily journal to look for things worth keeping. Promotion is what stops the journal growing forever and the durable memory staying empty.","default":7}},"type":"object","required":["subject_type","subject_id"],"title":"PromoteMemoryRequest","description":"Mirror of `PromoteRequest`."},"PromptGeneratorRequest":{"properties":{"list_id":{"type":"integer","title":"List Id"},"task_description":{"type":"string","title":"Task Description"}},"type":"object","required":["list_id","task_description"],"title":"PromptGeneratorRequest","description":"Ask the model to write an enrichment prompt from a list's columns."},"ProviderCatalogEntry":{"properties":{"provider":{"type":"string","title":"Provider"},"system_funded":{"type":"boolean","title":"System Funded","description":"True if graph8 holds a system-managed key for this provider (usable without BYOK; charges credits)."},"byok_configured":{"type":"boolean","title":"Byok Configured","description":"True if the org has an active BYOK key configured for this provider."},"default_credential_source":{"type":"string","enum":["system","byok"],"title":"Default Credential Source","description":"What credential_mode='auto' resolves to for this provider for this org right now."},"credits_per_row":{"additionalProperties":{"type":"number"},"type":"object","title":"Credits Per Row","description":"Per-action credit cost when run on graph8 system credentials (action -> credits/row)."},"actions":{"items":{"type":"string"},"type":"array","title":"Actions","description":"Action identifiers available for this provider."},"supported_fields":{"items":{"type":"string"},"type":"array","title":"Supported Fields","description":"Built-in fields (e.g. CONTACT_WORK_EMAIL) this provider can fill: it has a step in that field's recipe, so `field` + `providers=[...]` accepts it. Same set as `GET /enrichment/waterfall/templates`."},"default_for_fields":{"items":{"type":"string"},"type":"array","title":"Default For Fields","description":"Subset of `supported_fields` where the provider is in the recipe's default order."},"optional_for_fields":{"items":{"type":"string"},"type":"array","title":"Optional For Fields","description":"Subset of `supported_fields` where the provider is an opt-in choice: it only runs when you list it in `providers`, never in the default order."},"field_actions":{"additionalProperties":{"$ref":"#/components/schemas/ProviderFieldAction"},"type":"object","title":"Field Actions","description":"Per supported field: the action and output path the recipe uses for this provider."},"byok_connectable":{"type":"boolean","title":"Byok Connectable","description":"True when the org can save its own key for this provider (it is in the BYO credential catalog) or graph8 funds it. False means a step for it can only run for orgs that already hold a key.","default":false}},"type":"object","required":["provider","system_funded","byok_configured","default_credential_source"],"title":"ProviderCatalogEntry","description":"One enrichment provider in the catalog: its credential mode + credit cost.\n\nLets a caller see which providers graph8 funds (usable with no setup, charges\ncredits) vs which require the org's own API key (BYOK), before building a\npipeline — the programmatic equivalent of the UI's provider picker."},"ProviderCatalogResponse":{"properties":{"providers":{"items":{"$ref":"#/components/schemas/ProviderCatalogEntry"},"type":"array","title":"Providers"},"count":{"type":"integer","title":"Count","default":0}},"type":"object","title":"ProviderCatalogResponse","description":"Catalog of enrichment providers: which are graph8-funded (system) by default\nvs require the org's own key (BYOK), plus the credit cost per action."},"ProviderDomainResponse":{"properties":{"id":{"type":"integer","title":"Id"},"domain":{"type":"string","title":"Domain"},"source":{"type":"string","title":"Source","description":"How the domain entered the org, e.g. purchased | transferred | external"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"purchase_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Purchase Date"},"purchase_period":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Purchase Period"},"expires_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Expires At"},"is_transfer":{"type":"boolean","title":"Is Transfer","default":false},"is_external":{"type":"boolean","title":"Is External","default":false},"dns_zone_created":{"type":"boolean","title":"Dns Zone Created","default":false},"provider_connected":{"type":"boolean","title":"Provider Connected","description":"Whether this domain is connected to the managed mailbox-provisioning backend. Required before checkout-mailboxes will succeed for a managed purchase — connect it first with POST .../connect-provider."},"mailbox_count":{"type":"integer","title":"Mailbox Count","default":0},"created_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created By"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["id","domain","source","provider_connected"],"title":"ProviderDomainResponse","description":"A sending domain owned (or connected) by the org."},"ProviderFieldAction":{"properties":{"action":{"type":"string","title":"Action"},"output_field":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Output Field"},"optional":{"type":"boolean","title":"Optional","description":"True when the step is an opt-in choice, not part of the recipe's default order.","default":false}},"type":"object","required":["action"],"title":"ProviderFieldAction","description":"How a field's recipe uses one provider (additive catalog detail)."},"ProviderStepDetail":{"properties":{"provider":{"type":"string","title":"Provider"},"is_system_provider":{"type":"boolean","title":"Is System Provider","description":"True = uses graph8-managed system key (charges credits). False = uses org BYOK key."},"credential_source":{"type":"string","enum":["system","byok"],"title":"Credential Source","description":"'system' = graph8-funded; 'byok' = org's own key."},"credential_ready":{"type":"boolean","title":"Credential Ready","description":"True if the step can actually run: system steps are always ready; BYOK steps are ready only when the org has an active key for that provider."}},"type":"object","required":["provider","is_system_provider","credential_source","credential_ready"],"title":"ProviderStepDetail","description":"Per-step credential breakdown so callers can see, before running, which\nsteps use graph8 system keys (charge credits) vs the org's own BYOK key,\nand whether the required credential is actually present."},"ProviderUsagePayload":{"properties":{},"additionalProperties":true,"type":"object","title":"ProviderUsagePayload","description":"Usage figures per provider, or the result of a refresh/sync."},"ProviderUsageRefreshRequest":{"properties":{"provider_names":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Provider Names","description":"Only these providers. Omit for all."},"force_refresh":{"type":"boolean","title":"Force Refresh","description":"Refresh even if the figures are recent.","default":false}},"type":"object","title":"ProviderUsageRefreshRequest"},"ProvisioningStatesRequest":{"properties":{"mailbox_ids":{"items":{"type":"integer"},"type":"array","maxItems":50,"title":"Mailbox Ids","description":"Mailbox ids to report on. Up to 50."}},"type":"object","title":"ProvisioningStatesRequest","description":"Ask for the live provisioning step of up to 50 mailboxes."},"PublicCopilotRequest":{"properties":{"message":{"type":"string","title":"Message"},"session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Id"},"context":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Context"}},"type":"object","required":["message"],"title":"PublicCopilotRequest"},"PublicCopilotResponse":{"properties":{"response":{"type":"string","title":"Response"},"session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Id"},"sources":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Sources","default":[]}},"type":"object","required":["response"],"title":"PublicCopilotResponse"},"PublicEnrichRequest":{"properties":{"email":{"type":"string","title":"Email","description":"Email address to look up"}},"type":"object","required":["email"],"title":"PublicEnrichRequest"},"PublicEnrichResponse":{"properties":{"found":{"type":"boolean","title":"Found","description":"Whether the email was found in graph8"},"known_fields":{"additionalProperties":true,"type":"object","title":"Known Fields","description":"Fields graph8 already knows","default":{}},"missing_fields":{"items":{"type":"string"},"type":"array","title":"Missing Fields","description":"Fields the form should ask for","default":[]}},"type":"object","required":["found"],"title":"PublicEnrichResponse"},"PublishLandingPageRequest":{"properties":{"slug":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slug"},"domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain"},"domain_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Domain Id"},"subdomain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subdomain"},"path":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Path"},"override":{"type":"boolean","title":"Override","description":"Steal a URL already bound to another page. Default false.","default":false}},"type":"object","title":"PublishLandingPageRequest","description":"Where to publish. Every field optional - omit for the page's own slug.\n\n`override` true takes a URL that is already bound to a DIFFERENT page.\nThat page stops serving at it. Left false, a collision is refused."},"PublishSchemaVersionRequest":{"properties":{"objects":{"items":{},"type":"array","title":"Objects","description":"Declared custom objects, in `graph8.app.yaml` `objects:` shape."}},"type":"object","required":["objects"],"title":"PublishSchemaVersionRequest","description":"A schema publish carries ONLY declared objects.\n\nNot a whole `graph8.app.yaml`: `frontend`/`backend` are deploy-time build\nconfig (M6-5) and have no bearing on what a tenant's `cb_*` tables receive.\nAccepting them here would let a Dockerfile edit re-materialize every tenant."},"PublishSchemaVersionResponse":{"properties":{"version":{"$ref":"#/components/schemas/SchemaVersionResponse"},"created":{"type":"boolean","title":"Created","description":"False when an identical schema was already published -- the retry no-op."},"materialization":{"$ref":"#/components/schemas/MaterializationSummary"}},"type":"object","required":["version","created","materialization"],"title":"PublishSchemaVersionResponse","description":"The version, plus whether it was newly created and how the fan-out went."},"PullAllContactsRequest":{"properties":{"connection_id":{"type":"string","title":"Connection Id","description":"Which CRM connection to run against."},"limit":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Limit","description":"Ceiling on records processed. OMIT to take the app's own default (5,000 pulling, 10,000 pushing) rather than freezing a copy of it here."},"chunk_size":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Chunk Size","description":"Records per batch."},"max_parallel":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Max Parallel","description":"Concurrent batches."},"entity_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Type","default":"contacts"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id","description":"graph8 audience list to land in."},"enrich_from_graph8":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Enrich From Graph8","description":"Fill missing fields from the graph8 index as rows arrive. Omit to take the app's default - this SPENDS enrichment credit when on."}},"type":"object","required":["connection_id"],"title":"PullAllContactsRequest","description":"Pull every CRM contact into graph8."},"PullAllDealsRequest":{"properties":{"connection_id":{"type":"string","title":"Connection Id"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"crm_list_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Crm List Id"},"crm_list_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Crm List Title"},"limit":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Limit"},"chunk_size":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Chunk Size"}},"type":"object","required":["connection_id"],"title":"PullAllDealsRequest"},"PullAllLeadsRequest":{"properties":{"connection_id":{"type":"string","title":"Connection Id","description":"Which CRM connection to pull from."},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id","description":"graph8 audience to land the leads in."},"enrich_from_graph8":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Enrich From Graph8","description":"Fill missing fields from the graph8 index as rows arrive. This SPENDS ENRICHMENT CREDIT when on. Omit to take the app's default rather than turning a spend on by accident."},"source_mode":{"anyOf":[{"type":"string","enum":["all_leads","campaigns"]},{"type":"null"}],"title":"Source Mode","description":"`campaigns` restricts the pull to `campaign_ids`. Omit for the saved setting."},"campaign_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Campaign Ids","description":"Salesforce Campaign ids to pull members of."},"include_converted":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Include Converted","description":"Include leads Salesforce has already converted to a Contact."},"suppress_from_optouts":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Suppress From Optouts","description":"Skip leads that appear on an opt-out list."},"limit":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Limit","description":"Ceiling on records pulled."},"chunk_size":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Chunk Size","description":"Records per batch."},"max_parallel":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Max Parallel","description":"Concurrent batches."}},"type":"object","required":["connection_id"],"title":"PullAllLeadsRequest","description":"Pull Salesforce Leads into graph8.\n\nSending none of the optional fields runs the org's SAVED `pull.leads`\nsettings; sending any of them overrides those settings for this one run.\nThat is the app's behaviour and it is worth knowing, because an empty body\nhere is not \"pull everything\" - it is \"pull what I configured\"."},"PullCrmListRequest":{"properties":{"connection_id":{"type":"string","title":"Connection Id"},"crm_list_id":{"type":"string","title":"Crm List Id","description":"REQUIRED - the CRM list to pull."},"graph8_list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Graph8 List Id"},"auto_create_audience":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Auto Create Audience","description":"Create a matching graph8 audience if none is given."},"entity_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Type"},"limit":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Limit"},"reconcile":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Reconcile"},"enrich_from_graph8":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Enrich From Graph8","description":"SPENDS enrichment credit when on."}},"type":"object","required":["connection_id","crm_list_id"],"title":"PullCrmListRequest","description":"Pull ONE CRM list, rather than everything."},"PurchasePhoneRequest":{"properties":{"phone_number":{"type":"string","title":"Phone Number","description":"The number to buy, E.164 (e.g. `+14155550123`). Search for one first."},"provider":{"type":"string","enum":["twilio","telnyx"],"title":"Provider","description":"Which carrier to buy it from."},"assignee":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Assignee","description":"Who the number belongs to. Defaults to the identity behind the API key, matching the app - it is never taken from the body's organisation, because there is no organisation in the body."},"dialer":{"type":"boolean","title":"Dialer","description":"True provisions a dialer number; false provisions a voice-AI number.","default":true},"work":{"type":"boolean","title":"Work","description":"True makes this someone's personal work phone - provisioned like a dialer number but tagged `work`, and never part of the outbound caller-ID rotation pool.","default":false}},"type":"object","required":["phone_number","provider"],"title":"PurchasePhoneRequest","description":"Buy ONE number from the provider. THIS SPENDS CREDITS AND REAL MONEY.\n\nMirrors `phone_numbers.interfaces.fastapi.dtos.PurchasePhoneRequest`\nfield-for-field. `capabilities` is deliberately absent from both: it was\ndropped in the app on 2026-06-02 because the handler never read it and\nsending it silently 422'd."},"PushAllContactsRequest":{"properties":{"connection_id":{"type":"string","title":"Connection Id","description":"Which CRM connection to run against."},"limit":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Limit","description":"Ceiling on records processed. OMIT to take the app's own default (5,000 pulling, 10,000 pushing) rather than freezing a copy of it here."},"chunk_size":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Chunk Size","description":"Records per batch."},"max_parallel":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Max Parallel","description":"Concurrent batches."},"entity_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Type","default":"contacts"},"use_file_import":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Use File Import","description":"Use the provider's bulk file import instead of the API."},"file_import_threshold":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"File Import Threshold"},"crm_list_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Crm List Id","description":"Target list in the CRM."},"sync_list_mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sync List Mode"}},"type":"object","required":["connection_id"],"title":"PushAllContactsRequest","description":"Push every graph8 contact into the CRM."},"PushAllDealsRequest":{"properties":{"connection_id":{"type":"string","title":"Connection Id"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"crm_list_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Crm List Id"},"sync_list_mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sync List Mode"},"limit":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Limit"},"chunk_size":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Chunk Size"}},"type":"object","required":["connection_id"],"title":"PushAllDealsRequest"},"PushAllLeadsRequest":{"properties":{"connection_id":{"type":"string","title":"Connection Id","description":"Which CRM connection to push into."},"limit":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Limit","description":"Ceiling on records pushed. Omit for the app's default."},"chunk_size":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Chunk Size","description":"Records per batch."},"max_parallel":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Max Parallel","description":"Concurrent batches."},"use_file_import":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Use File Import","description":"Use the provider's bulk file import instead of the API."},"file_import_threshold":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"File Import Threshold","description":"Record count above which the file import is used."},"crm_list_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Crm List Id","description":"Target list in the CRM."},"sync_list_mode":{"anyOf":[{"type":"string","enum":["no_list","new_list","existing_list"]},{"type":"null"}],"title":"Sync List Mode","description":"`no_list` (the app's default), `new_list` or `existing_list`. Sending `crm_list_id` with no mode implies `existing_list`."},"source_mode":{"anyOf":[{"type":"string","enum":["all_qualified","saved_segment","segments_union","all_contacts"]},{"type":"null"}],"title":"Source Mode","description":"Which population to push. `saved_segment` REQUIRES `audience_id`; `segments_union` REQUIRES `audience_ids`. Omit for the app's default (`all_qualified`)."},"audience_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Audience Id","description":"graph8 audience for `saved_segment`."},"audience_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Audience Ids","description":"graph8 audiences for `segments_union`."},"salesforce_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Salesforce Campaign Id","description":"Add every pushed lead to this Salesforce Campaign as a CampaignMember."},"lead_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Lead Id","description":"Push a single graph8 lead row."},"status_qualified":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status Qualified","description":"Salesforce `Lead.Status` API name to set on qualified leads. Read the valid values from `/integrations/crm-sync/leads/statuses` - Lead.Status is an OPEN picklist, so Salesforce stores whatever is sent and an invented value silently becomes a real status."},"status_unqualified":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status Unqualified","description":"Salesforce `Lead.Status` API name for unqualified leads."},"large_population_confirmed":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Large Population Confirmed","description":"Acknowledge that this job covers a population large enough that the app asks first. Leave unset to keep that refusal in place; set true ONLY when you have read the preview's record count and accept it. This is a safety interlock, not a tuning option - the records land in the customer's Salesforce and cannot be un-pushed."},"auto_assign_on_create":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Auto Assign On Create","description":"Run Salesforce's assignment rules on each created lead."}},"type":"object","required":["connection_id"],"title":"PushAllLeadsRequest","description":"Push graph8 people into Salesforce as first-class Leads.\n\nSalesforce is the CRM that distinguishes a Lead from a Contact; the other\nproviders do not, which is why this is a separate surface from\n`/integrations/crm-sync/contacts/push` rather than an `entity_type` on it."},"PushAudienceRequest":{"properties":{"connection_id":{"type":"string","title":"Connection Id","description":"Which CRM connection to run against."},"limit":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Limit","description":"Ceiling on records processed. OMIT to take the app's own default (5,000 pulling, 10,000 pushing) rather than freezing a copy of it here."},"chunk_size":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Chunk Size","description":"Records per batch."},"max_parallel":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Max Parallel","description":"Concurrent batches."},"audience_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Audience Id","description":"graph8 audience to push."},"entity_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Type"},"use_file_import":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Use File Import"},"file_import_threshold":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"File Import Threshold"},"crm_list_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Crm List Id"},"reconcile":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Reconcile","description":"Reconcile against what is already in the CRM first."}},"type":"object","required":["connection_id"],"title":"PushAudienceRequest","description":"Push ONE audience, rather than everything."},"PutAppSecretRequest":{"properties":{"provider_ref":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Provider Ref","description":"Secret-manager PATH for the value. Never the value itself."}},"type":"object","title":"PutAppSecretRequest","description":"Declare (or rotate) one secret.\n\n`provider_ref` is the ONLY writable field, and it is a pointer. A `value`\nfield here would make every backup of the control plane a place credentials\nleak from, which is why the table has no column for one."},"QuestionAnswerUpdateRequest":{"properties":{"final_answer":{"type":"string","title":"Final Answer","description":"The edited answer text."}},"type":"object","required":["final_answer"],"title":"QuestionAnswerUpdateRequest","description":"Replace one question's answer.\n\nMirrors `security_questionnaires.UpdateAnswerRequest`. This is the human\nedit: the answer becomes the one the filled workbook carries."},"QuestionCreateRequest":{"properties":{"chat_bot_id":{"type":"string","title":"Chat Bot Id","description":"Owning chat bot id (UUID)."},"question":{"type":"string","maxLength":1000,"minLength":1,"title":"Question"},"category":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Category"},"paths":{"items":{"type":"string"},"type":"array","title":"Paths"},"active":{"type":"boolean","title":"Active","default":true},"surface":{"anyOf":[{"type":"string","enum":["external","internal"]},{"type":"null"}],"title":"Surface","description":"NULL shows it on BOTH widgets."},"placements":{"anyOf":[{"items":{"type":"string","enum":["launcher","home","conversation"]},"type":"array"},{"type":"null"}],"title":"Placements","description":"NULL or [] means every placement."},"sort_order":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Sort Order","description":"Order within a placement. NULL sorts last."}},"type":"object","required":["chat_bot_id","question"],"title":"QuestionCreateRequest","description":"A preset question the widget offers.\n\n`placements` NULL or empty means ALL placements, not none - the app treats\nthe absent case as unrestricted, and reading it the other way would hide\nevery question a caller created without naming one."},"QuestionNoteRequest":{"properties":{"notes":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Notes","description":"Why. Shown to whoever picks the question up."}},"type":"object","title":"QuestionNoteRequest","description":"The note attached to an escalate / skip / mark-wrong decision.\n\nMirrors `security_questionnaires.EscalateRequest`. One model in the app\nserves all three routes, so it is one model here too rather than three\nidentical ones that could drift apart."},"QuestionUpdateRequest":{"properties":{"chat_bot_id":{"type":"string","title":"Chat Bot Id","description":"Owning chat bot id (UUID)."},"question":{"anyOf":[{"type":"string","maxLength":1000,"minLength":1},{"type":"null"}],"title":"Question"},"category":{"anyOf":[{"type":"string","maxLength":100,"minLength":1},{"type":"null"}],"title":"Category"},"paths":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Paths"},"active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Active"},"surface":{"anyOf":[{"type":"string","enum":["external","internal"]},{"type":"null"}],"title":"Surface"},"expected_revision":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Expected Revision"},"placements":{"anyOf":[{"items":{"type":"string","enum":["launcher","home","conversation"]},"type":"array"},{"type":"null"}],"title":"Placements"},"sort_order":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Sort Order"}},"type":"object","required":["chat_bot_id"],"title":"QuestionUpdateRequest","description":"Partial edit of a preset question. `chat_bot_id` locates the row."},"QuestionnaireUpdateRequest":{"properties":{"display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display Name","description":"User-friendly name for the questionnaire."}},"type":"object","title":"QuestionnaireUpdateRequest","description":"Rename a questionnaire.\n\nMirrors `security_questionnaires.UpdateQuestionnaireRequest`. Metadata\nonly - it never touches an answer."},"QuotableProductsResponse":{"properties":{"items":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Items"},"total":{"type":"integer","title":"Total"},"page":{"type":"integer","title":"Page"},"limit":{"type":"integer","title":"Limit"}},"type":"object","required":["items","total","page","limit"],"title":"QuotableProductsResponse","description":"``GET /quotable-products`` envelope (pagination preserved)."},"QuoteApprovalDecisionRequest":{"properties":{"comment":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Comment"},"reason":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Reason"}},"type":"object","title":"QuoteApprovalDecisionRequest","description":"Approve or reject a quote that is awaiting approval. Mirrors `QuoteApprovalDecisionDTO`.\n\n`reason` is accepted as another name for `comment`; send one. A rejection\nREQUIRES the text (400 without it), and it is recorded on the quote."},"QuoteBillingContactCreateRequest":{"properties":{"mashup_company_id":{"type":"integer","minimum":1.0,"title":"Mashup Company Id","description":"Company the contact belongs to."},"deal_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Deal Id"},"name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Name"},"email":{"type":"string","maxLength":255,"title":"Email"}},"type":"object","required":["mashup_company_id","email"],"title":"QuoteBillingContactCreateRequest","description":"The FINANCE contact a quote bills to - name and email only."},"QuoteCatalogValidateLine":{"properties":{"manual_product_id":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Manual Product Id"},"name":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Name"},"base_name":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Base Name"},"category":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Category"}},"type":"object","title":"QuoteCatalogValidateLine","description":"One selected catalog line. Mirrors `CatalogValidateLineDTO`.\n\nWith `manual_product_id` the server resolves name, base name and category\nfrom the catalog itself; custom one-off lines omit the id and carry their own."},"QuoteCatalogValidateRequest":{"properties":{"line_items":{"items":{"$ref":"#/components/schemas/QuoteCatalogValidateLine"},"type":"array","maxItems":500,"title":"Line Items"}},"type":"object","title":"QuoteCatalogValidateRequest","description":"Check a product selection against the catalog's rules. Mirrors `CatalogValidateDTO`."},"QuoteContactCreateRequest":{"properties":{"email":{"type":"string","maxLength":320,"minLength":3,"title":"Email"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"department":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Department"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone"},"mobile_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mobile Phone"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url"},"buying_role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Buying Role"},"mashup_company_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Mashup Company Id","description":"Company to link the new contact to."},"deal_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Deal Id","description":"Deal to link it to."}},"type":"object","required":["email"],"title":"QuoteContactCreateRequest","description":"The full CRM contact form for a quote's SIGNER.\n\nDistinct from the billing contact below, which is a finance contact and\ntakes name and email only. This one links the new contact to the deal and\nthe company so it is immediately usable as the signer."},"QuoteCreateRequest":{"properties":{"title":{"type":"string","maxLength":500,"minLength":1,"title":"Title"},"mashup_company_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Mashup Company Id"},"signer_contact_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Signer Contact Id"},"signer_email":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Signer Email"},"signer_name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Signer Name"},"billing_contact_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Billing Contact Id"},"billing_legal_name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Billing Legal Name"},"billing_primary_email":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Billing Primary Email"},"billing_email":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Billing Email"},"billing_address":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Billing Address"},"deal_id":{"type":"string","title":"Deal Id"},"owner_id":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Owner Id"},"template_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Template Id"},"currency":{"type":"string","maxLength":3,"minLength":3,"title":"Currency","default":"USD"},"payment_terms":{"type":"string","enum":["due_on_receipt","net_15","net_30","net_45","net_60","net_90"],"title":"Payment Terms","default":"net_30"},"valid_until":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Valid Until"},"terms_content":{"anyOf":[{"type":"string","maxLength":50000},{"type":"null"}],"title":"Terms Content"},"privacy_content":{"anyOf":[{"type":"string","maxLength":50000},{"type":"null"}],"title":"Privacy Content"},"notes":{"anyOf":[{"type":"string","maxLength":10000},{"type":"null"}],"title":"Notes"},"public_notes":{"anyOf":[{"type":"string","maxLength":50000},{"type":"null"}],"title":"Public Notes"},"tax_amount":{"type":"integer","maximum":1000000000.0,"minimum":0.0,"title":"Tax Amount","default":0},"line_items":{"items":{"$ref":"#/components/schemas/QuoteLineItemRequest"},"type":"array","minItems":1,"title":"Line Items"},"contract_months":{"anyOf":[{"type":"number","maximum":120.0,"minimum":0.1},{"type":"null"}],"title":"Contract Months"},"contract_duration_value":{"anyOf":[{"type":"number","maximum":3650.0,"minimum":0.1},{"type":"null"}],"title":"Contract Duration Value"},"contract_duration_unit":{"anyOf":[{"type":"string","enum":["months","weeks","days"]},{"type":"null"}],"title":"Contract Duration Unit"},"contract_start_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contract Start Date"},"contract_end_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contract End Date"},"accepted_payment_methods":{"anyOf":[{"items":{"type":"string","enum":["ach","credit_card","wire"]},"type":"array"},{"type":"null"}],"title":"Accepted Payment Methods"},"marketing_rights":{"anyOf":[{"items":{"type":"string","enum":["logo","quote","case_study"]},"type":"array"},{"type":"null"}],"title":"Marketing Rights"}},"type":"object","required":["title","deal_id","line_items"],"title":"QuoteCreateRequest","description":"Create a new quote (always starts in `draft` status).\n\nMirrors ``CreateQuoteDTO``. At least one of ``signer_contact_id`` or\n``signer_email`` is required. ``line_items`` must be non-empty —\nzero-line quotes can't be invoiced. ``deal_id`` is required: every new\nquote must be linked to an existing deal (422 otherwise); the company\ndefaults to the deal's company when omitted."},"QuoteDetail":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"quote_number":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Quote Number"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"line_items":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Line Items"},"activity":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Activity"},"envelope":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Envelope"}},"additionalProperties":true,"type":"object","title":"QuoteDetail","description":"Full row + line items + activity + envelope from ``GET /quotes/{id}``.\n\nOpen dict because ``_get_quote_detail`` returns the dynamic\n``_row_to_dict`` shape plus resolved contact/company/envelope blocks."},"QuoteLineItem":{"properties":{"product_name":{"type":"string","maxLength":255,"minLength":1,"title":"Product Name"},"unit_amount":{"type":"integer","maximum":1000000000.0,"minimum":0.0,"title":"Unit Amount","description":"CENTS, not dollars."},"stripe_product_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stripe Product Id"},"stripe_price_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stripe Price Id"},"manual_product_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Manual Product Id"},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description"},"quantity":{"type":"integer","maximum":10000.0,"minimum":1.0,"title":"Quantity","default":1},"discount_pct":{"type":"number","maximum":100.0,"minimum":0.0,"title":"Discount Pct","default":0},"billing_frequency":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Billing Frequency"},"start_month":{"type":"integer","maximum":120.0,"minimum":1.0,"title":"Start Month","default":1},"billing_start_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Billing Start Date"},"sort_order":{"type":"integer","title":"Sort Order","default":0}},"additionalProperties":false,"type":"object","required":["product_name","unit_amount"],"title":"QuoteLineItem","description":"One priced line, mirroring the app's `LineItemDTO`.\n\nThe two REQUIRED fields are required here too, and that is the point: the\napp model is built inside the handler, so a missing `product_name` or\n`unit_amount` would raise a bare `pydantic.ValidationError` there - not the\n`RequestValidationError` `error_handlers.py` registers - and escape as a\n500 instead of a 422.\n\n`unit_amount` is in CENTS, like the app. An API that took dollars here\nwhile the app took cents would be wrong by a factor of a hundred on every\nquote, silently.\n\nCLOSED (`extra=\"forbid\"`), which makes this stricter than the app on\npurpose. `LineItemDTO` uses pydantic's default behaviour and DROPS an\nunrecognised field, so an open model here would accept a pricing field,\nlose it on the way in, and return a schedule computed without it. On a\nmoney surface a 422 naming the field is worth more than a 200 that quietly\npriced something else. Nothing existing is affected - this route is new."},"QuoteLineItemRequest":{"properties":{"stripe_product_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stripe Product Id"},"stripe_price_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stripe Price Id"},"manual_product_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Manual Product Id"},"product_name":{"type":"string","maxLength":255,"minLength":1,"title":"Product Name"},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description"},"quantity":{"type":"integer","maximum":10000.0,"minimum":1.0,"title":"Quantity","default":1},"unit_amount":{"type":"integer","maximum":1000000000.0,"minimum":0.0,"title":"Unit Amount","description":"In cents"},"discount_pct":{"type":"number","maximum":100.0,"minimum":0.0,"title":"Discount Pct","default":0},"billing_frequency":{"anyOf":[{"type":"string","enum":["one_time","month","year","quarter"]},{"type":"null"}],"title":"Billing Frequency"},"start_month":{"type":"integer","maximum":120.0,"minimum":1.0,"title":"Start Month","description":"Contract month when recurring billing begins; 1 means at contract start. Use billing_start_date instead for an exact date.","default":1},"billing_start_date":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"Billing Start Date","description":"Exact recurring billing start date within the contract; start_month must remain 1 when supplied."},"sort_order":{"type":"integer","title":"Sort Order","default":0}},"type":"object","required":["product_name","unit_amount"],"title":"QuoteLineItemRequest","description":"One line item on a quote request body.\n\nShape mirrors ``integrations_v4.interfaces.fastapi.quote_router.LineItemDTO``\nexactly. Pass either ``stripe_product_id`` + ``stripe_price_id`` (for a\nStripe-catalogue product) or ``manual_product_id`` (for an org-owned\nmanual catalogue entry), or neither (for a custom one-off line).\nAuthorization is enforced server-side — non-quotable products are\nrejected with 400."},"QuoteListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"QuoteListPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape."},"QuoteListResponse":{"properties":{"items":{"items":{"$ref":"#/components/schemas/QuoteSummary"},"type":"array","title":"Items"},"total":{"type":"integer","title":"Total"},"page":{"type":"integer","title":"Page"},"limit":{"type":"integer","title":"Limit"}},"type":"object","required":["items","total","page","limit"],"title":"QuoteListResponse","description":"``GET /quotes`` envelope — preserves the original list endpoint's\npagination fields verbatim (the internal handler returns\n``{items, total, page, limit}``)."},"QuotePayload":{"properties":{},"additionalProperties":true,"type":"object","title":"QuotePayload","description":"An open envelope for a quote, template, contact or job result."},"QuotePaymentInstallment":{"properties":{"id":{"type":"string","maxLength":50,"minLength":1,"title":"Id"},"percentage":{"anyOf":[{"type":"number","minimum":0.0},{"type":"string"}],"title":"Percentage"},"amount_cents":{"type":"integer","maximum":1000000000.0,"minimum":0.0,"title":"Amount Cents"},"due_type":{"type":"string","enum":["milestone","date"],"title":"Due Type"},"due_label":{"type":"string","maxLength":200,"title":"Due Label"},"sort_order":{"type":"integer","minimum":0.0,"title":"Sort Order"}},"type":"object","required":["id","percentage","amount_cents","due_type","due_label","sort_order"],"title":"QuotePaymentInstallment","description":"One installment of a payment schedule. Mirrors `PaymentInstallmentDTO`.\n\n`due_type` is `milestone` (free-text `due_label`) or `date` (ISO date as `due_label`)."},"QuotePaymentInstallmentsRequest":{"properties":{"total_cents":{"type":"integer","maximum":1000000000.0,"minimum":0.0,"title":"Total Cents"},"installments":{"items":{"$ref":"#/components/schemas/QuotePaymentInstallment"},"type":"array","title":"Installments"}},"type":"object","required":["total_cents","installments"],"title":"QuotePaymentInstallmentsRequest","description":"Work out installment amounts from percentages. Mirrors `QuotePaymentInstallmentsDTO`.\n\nArithmetic over the body: nothing is read or written."},"QuoteSendPreviewRequest":{"properties":{"subject":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subject"},"message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Message"},"email_body":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email Body"},"recipient_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Recipient Email"},"recipient_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Recipient Name"},"cc_emails":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Cc Emails"},"recipients":{"anyOf":[{"items":{"$ref":"#/components/schemas/QuoteSendRecipient"},"type":"array"},{"type":"null"}],"title":"Recipients"},"notification_mode":{"type":"string","enum":["after_each","after_all"],"title":"Notification Mode","default":"after_each"},"preview_recipient_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Preview Recipient Email"},"deliver":{"type":"boolean","title":"Deliver","default":true}},"type":"object","title":"QuoteSendPreviewRequest","description":"The same body `POST /quotes/{id}/send` takes - rendered, not sent.\n\nIdentical on purpose: previewing with a different body than you send is\nhow a preview stops predicting anything. `deliver` is accepted because the\napp's model has it, and it is INERT here - this handler renders and\nreturns, and nothing in it reaches a mail transport."},"QuoteSendRecipient":{"properties":{"email":{"type":"string","maxLength":255,"title":"Email"},"name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Name"},"role":{"type":"string","enum":["signer","viewer"],"title":"Role","default":"signer"},"subject":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Subject"},"email_body":{"anyOf":[{"type":"string","maxLength":10000},{"type":"null"}],"title":"Email Body"}},"type":"object","required":["email"],"title":"QuoteSendRecipient","description":"One recipient of a quote preview."},"QuoteSendRequest":{"properties":{"subject":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subject"},"message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Message"}},"type":"object","title":"QuoteSendRequest","description":"Send (or resend) a quote for e-signature.\n\nBoth fields are optional — the server falls back to the quote title\nfor ``subject`` and a default cover line for ``message``. When the\ntarget quote already has an active envelope (``sent`` / ``viewed``)\nthis resends without minting a new signing link."},"QuoteSettingsResponse":{"properties":{},"additionalProperties":true,"type":"object","title":"QuoteSettingsResponse","description":"``GET /quote-settings`` row. Open dict — settings columns evolve\nindependently of this API surface."},"QuoteSettingsUpdateRequest":{"properties":{"company_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Name"},"company_logo_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Logo Url"},"default_terms":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Default Terms"},"default_privacy":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Default Privacy"},"terms_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Terms Url"},"privacy_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Privacy Url"},"default_payment_terms":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Default Payment Terms"},"default_valid_days":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Default Valid Days"},"quote_number_prefix":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Quote Number Prefix"},"accent_color":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Accent Color"},"footer_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Footer Text"},"terms_library":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Terms Library"},"sender_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sender Name"},"sender_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sender Email","description":"Whose name every quote goes out under. Admin-only for that reason."},"sender_mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sender Mode","description":"`fixed` to always use `sender_email`, or `creator`."},"company_address":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Address"},"company_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Phone"},"company_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Email"},"quote_acceptance_roam_notifications_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Quote Acceptance Roam Notifications Enabled"},"quote_acceptance_roam_channel_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Quote Acceptance Roam Channel Id"},"quote_acceptance_roam_channel_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Quote Acceptance Roam Channel Name"},"auto_close_deal_on_acceptance":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Auto Close Deal On Acceptance","description":"Close the linked DEAL when a quote is accepted. Org-wide, and it changes what every future acceptance does to the pipeline."},"auto_advance_deal_on_quote_send":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Auto Advance Deal On Quote Send"},"default_billing_provider":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Default Billing Provider"},"required_billing_fields":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Required Billing Fields"}},"type":"object","title":"QuoteSettingsUpdateRequest","description":"Org-wide quote branding, terms and sender identity.\n\nA CLOSED mirror of the app's `QuoteSettingsDTO`, not an open bag. Leaving\nit open would have achieved nothing: the app model uses pydantic's default\n`extra` behaviour, so an unrecognised branding field is dropped THERE\nwhatever this one does. Closed, the caller gets a 422 naming the field;\nopen, they get a 200 and settings that did not change.\n\nEvery field is optional, and the app writes with `exclude_none`, so a\nfield you omit is left alone rather than blanked."},"QuoteSummary":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"quote_number":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Quote Number"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"total":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Total"},"currency":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Currency"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"sent_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sent At"},"accepted_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Accepted At"}},"additionalProperties":true,"type":"object","title":"QuoteSummary","description":"List-view row from ``GET /quotes``. ``extra=\"allow\"`` keeps every\nbackend column flowing through without us re-declaring CBQuote."},"QuoteTemplateRequest":{"properties":{"name":{"type":"string","maxLength":255,"minLength":1,"title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"default_line_items":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Default Line Items"},"default_payment_terms":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Default Payment Terms"},"default_valid_days":{"anyOf":[{"type":"integer","maximum":365.0,"minimum":1.0},{"type":"null"}],"title":"Default Valid Days"},"terms_override":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Terms Override"},"is_default":{"type":"boolean","title":"Is Default","default":false},"document_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Document Ids","description":"Legal documents to attach to every quote built from this template. Ids come from `GET /quote-settings/documents`."},"contract_months":{"anyOf":[{"type":"number","maximum":120.0,"minimum":0.1},{"type":"null"}],"title":"Contract Months"},"contract_duration_value":{"anyOf":[{"type":"number","maximum":3650.0,"minimum":0.1},{"type":"null"}],"title":"Contract Duration Value"},"contract_duration_unit":{"anyOf":[{"type":"string","enum":["months","weeks","days"]},{"type":"null"}],"title":"Contract Duration Unit"}},"type":"object","required":["name"],"title":"QuoteTemplateRequest","description":"A reusable quote template. A CLOSED mirror of `QuoteTemplateDTO` - the\napp drops an unrecognised field silently, so an open model here would turn\na typo into a template saved without the thing you typed."},"QuoteUpdateRequest":{"properties":{"title":{"anyOf":[{"type":"string","maxLength":500,"minLength":1},{"type":"null"}],"title":"Title"},"mashup_company_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Mashup Company Id"},"signer_contact_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Signer Contact Id"},"signer_email":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Signer Email"},"signer_name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Signer Name"},"billing_contact_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Billing Contact Id"},"billing_legal_name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Billing Legal Name"},"billing_primary_email":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Billing Primary Email"},"billing_email":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Billing Email"},"billing_address":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Billing Address"},"deal_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Deal Id"},"owner_id":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Owner Id"},"currency":{"anyOf":[{"type":"string","maxLength":3,"minLength":3},{"type":"null"}],"title":"Currency"},"payment_terms":{"anyOf":[{"type":"string","enum":["due_on_receipt","net_15","net_30","net_45","net_60","net_90"]},{"type":"null"}],"title":"Payment Terms"},"valid_until":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Valid Until"},"terms_content":{"anyOf":[{"type":"string","maxLength":50000},{"type":"null"}],"title":"Terms Content"},"privacy_content":{"anyOf":[{"type":"string","maxLength":50000},{"type":"null"}],"title":"Privacy Content"},"notes":{"anyOf":[{"type":"string","maxLength":10000},{"type":"null"}],"title":"Notes"},"public_notes":{"anyOf":[{"type":"string","maxLength":50000},{"type":"null"}],"title":"Public Notes"},"tax_amount":{"anyOf":[{"type":"integer","maximum":1000000000.0,"minimum":0.0},{"type":"null"}],"title":"Tax Amount"},"line_items":{"anyOf":[{"items":{"$ref":"#/components/schemas/QuoteLineItemRequest"},"type":"array","minItems":1},{"type":"null"}],"title":"Line Items"},"contract_months":{"anyOf":[{"type":"number","maximum":120.0,"minimum":0.1},{"type":"null"}],"title":"Contract Months"},"contract_duration_value":{"anyOf":[{"type":"number","maximum":3650.0,"minimum":0.1},{"type":"null"}],"title":"Contract Duration Value"},"contract_duration_unit":{"anyOf":[{"type":"string","enum":["months","weeks","days"]},{"type":"null"}],"title":"Contract Duration Unit"},"contract_start_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contract Start Date"},"contract_end_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contract End Date"},"accepted_payment_methods":{"anyOf":[{"items":{"type":"string","enum":["ach","credit_card","wire"]},"type":"array"},{"type":"null"}],"title":"Accepted Payment Methods"},"marketing_rights":{"anyOf":[{"items":{"type":"string","enum":["logo","quote","case_study"]},"type":"array"},{"type":"null"}],"title":"Marketing Rights"}},"type":"object","title":"QuoteUpdateRequest","description":"Partial update for a draft quote.\n\nAll fields optional. Passing ``line_items`` replaces them entirely\n(and re-runs quotable-product authorization). Quotes in any status\nother than ``draft`` reject updates with 400 — use ``edit-as-draft``\non a ``sent`` quote, or ``duplicate`` on a terminal one, to get a\nfresh editable copy."},"RadarAlerts":{"properties":{"pricing_change":{"type":"boolean","title":"Pricing Change","default":true},"new_ads":{"type":"boolean","title":"New Ads","default":true},"content_velocity":{"type":"boolean","title":"Content Velocity","default":true},"keyword_overtake":{"type":"boolean","title":"Keyword Overtake","default":true},"warm_account":{"type":"boolean","title":"Warm Account","default":true},"case_files":{"type":"boolean","title":"Case Files","default":true},"hiring_spike":{"type":"boolean","title":"Hiring Spike","default":true}},"type":"object","title":"RadarAlerts"},"RadarCaseFileActionRequest":{"properties":{"action":{"type":"string","enum":["mark_played","dismiss"],"title":"Action"}},"type":"object","required":["action"],"title":"RadarCaseFileActionRequest"},"RadarChannels":{"properties":{"in_app":{"type":"boolean","title":"In App","default":true},"bridge":{"type":"boolean","title":"Bridge","default":false}},"type":"object","title":"RadarChannels"},"RadarReportCreateRequest":{"properties":{"audience":{"type":"string","enum":["executive","developer"],"title":"Audience"},"capability_id":{"type":"string","title":"Capability Id"},"edge":{"type":"string","enum":["us","them"],"title":"Edge"}},"type":"object","required":["audience","capability_id","edge"],"title":"RadarReportCreateRequest"},"RadarReportListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"RadarReportListPayload","description":"A list of reports or case files under `items`."},"RadarReportPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"RadarReportPayload","description":"A deep-dive report, case file, dossier or leaderboard."},"RadarSettings":{"properties":{"tier1_cadence_days":{"type":"integer","maximum":365.0,"minimum":1.0,"title":"Tier1 Cadence Days","default":7},"tier2_cadence_days":{"type":"integer","maximum":365.0,"minimum":1.0,"title":"Tier2 Cadence Days","default":30},"alerts":{"$ref":"#/components/schemas/RadarAlerts"},"channels":{"$ref":"#/components/schemas/RadarChannels"},"ad_source":{"type":"string","enum":["stored","linkedin","meta","google","all"],"title":"Ad Source","default":"stored"},"monthly_credit_cap":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Monthly Credit Cap"}},"type":"object","title":"RadarSettings"},"RateCardUpdateRequest":{"properties":{"monthly_rate_usd":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Monthly Rate Usd","description":"Monthly base rate, e.g. '2500.00'."},"per_meeting_rate_usd":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Per Meeting Rate Usd","description":"Per-meeting rate, e.g. '75.00'."},"availability_status":{"anyOf":[{"type":"string","enum":["open","limited","fully_booked","hidden"]},{"type":"null"}],"title":"Availability Status"},"bio":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bio"}},"type":"object","title":"RateCardUpdateRequest","description":"The published rate card. This is the price a client is billed."},"ReassignListOwnerRequest":{"properties":{"owner_user_id":{"type":"string","maxLength":255,"minLength":1,"title":"Owner User Id"},"owner_email":{"type":"string","format":"email","title":"Owner Email","description":"Must agree with the user id - the app verifies both. Typed as an email at the request layer because the app's model is `EmailStr` and is built inside the handler: a malformed address would otherwise raise there and escape as a 500 rather than a 422."},"mode":{"type":"string","enum":["list_only","list_and_records"],"title":"Mode","description":"`list_only` moves just the list. `list_and_records` also re-owns every record in it, which can change who else can see them.","default":"list_only"}},"type":"object","required":["owner_user_id","owner_email"],"title":"ReassignListOwnerRequest","description":"Hand a list to someone else.\n\n`mode` decides how far the transfer reaches, and the difference is not\ncosmetic: `list_and_records` re-owns every CONTACT in the list as well,\nwhich changes who can see them under record-level scoping. Preview it\nfirst with `GET /lists/{id}/owner/preview`."},"RecalculateResponse":{"properties":{"queued":{"type":"boolean","title":"Queued"}},"type":"object","required":["queued"],"title":"RecalculateResponse"},"RecordBulkArchiveRequest":{"properties":{"record_ids":{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":500,"minItems":1,"title":"Record Ids"}},"type":"object","required":["record_ids"],"title":"RecordBulkArchiveRequest","description":"Body of ``POST /{slug}/records/bulk-archive`` and ``.../bulk-restore``:\nan explicit id list, capped at 500 like the bulk update."},"RecordBulkArchiveResponse":{"properties":{"succeeded":{"items":{"type":"string","format":"uuid"},"type":"array","title":"Succeeded"},"failed":{"items":{"$ref":"#/components/schemas/RecordBulkUpdateFailure"},"type":"array","title":"Failed"}},"type":"object","required":["succeeded","failed"],"title":"RecordBulkArchiveResponse","description":"``succeeded`` lists exactly the records this call changed, so a bulk\nrestore of ``succeeded`` is the exact inverse of a bulk archive. ``failed``\nuses the bulk-update failure shape; codes: not_found, already_archived\n(archive), not_archived (restore), locked, invalid_value, unique_conflict,\nconstraint_violation or rejected."},"RecordBulkUpdate":{"properties":{"record_ids":{"anyOf":[{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":500},{"type":"null"}],"title":"Record Ids"},"filters":{"anyOf":[{"items":{"$ref":"#/components/schemas/RecordFilter"},"type":"array","maxItems":10},{"type":"null"}],"title":"Filters"},"after_record_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"After Record Id"},"values":{"additionalProperties":true,"type":"object","title":"Values"}},"type":"object","title":"RecordBulkUpdate","description":"Bulk-update body: exactly one scope (explicit ids or a filtered set),\nplus the values to apply to every record in that scope.\n\n``record_ids`` is capped at 500 to bound the transaction. ``filters`` reuses\nthis router's own ``RecordFilter`` shape; a filtered scope is resolved\nentirely server-side (ordered by record id, at most 500 per call) and the\nids it resolves are never trusted from the client. ``after_record_id``\ncontinues a filtered scope that the previous call reported as truncated."},"RecordBulkUpdateFailure":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"error":{"type":"string","title":"Error"},"code":{"type":"string","title":"Code","default":"rejected"},"attribute_slug":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Attribute Slug"}},"type":"object","required":["id","error"],"title":"RecordBulkUpdateFailure","description":"One record a bulk update did not change. ``error`` is the human message\n(kept for existing clients); ``code`` is stable for UIs to branch on:\nlocked, archived, not_found, scope_changed, unique_conflict, invalid_value,\nconstraint_violation or rejected; ``attribute_slug`` names the field when\none field caused it."},"RecordBulkUpdateResponse":{"properties":{"succeeded":{"items":{"type":"string","format":"uuid"},"type":"array","title":"Succeeded"},"failed":{"items":{"$ref":"#/components/schemas/RecordBulkUpdateFailure"},"type":"array","title":"Failed"},"truncated":{"type":"boolean","title":"Truncated","default":false},"next_after_record_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Next After Record Id"}},"type":"object","required":["succeeded","failed"],"title":"RecordBulkUpdateResponse"},"RecordColumnValuesRequest":{"properties":{"list_id":{"type":"integer","title":"List Id","description":"List the record is read through."},"record_id":{"type":"integer","title":"Record Id","description":"Record primary key."}},"type":"object","required":["list_id","record_id"],"title":"RecordColumnValuesRequest","description":"Read every column value for ONE row, resolved against a list.\n\nThe list decides whether `record_id` is read as a contact or a company,\nand which list-scoped custom columns are in play - which is why it is\nrequired rather than inferred."},"RecordFilter":{"properties":{"attribute_slug":{"type":"string","title":"Attribute Slug"},"operator":{"type":"string","enum":["eq","ne","gt","gte","lt","lte","contains","starts_with","in","is_null","is_not_null"],"title":"Operator"},"value":{"anyOf":[{},{"type":"null"}],"title":"Value"}},"type":"object","required":["attribute_slug","operator"],"title":"RecordFilter","description":"Filter parameters for listing records."},"RecordHistoryEntry":{"properties":{"attribute":{"type":"string","title":"Attribute","description":"Attribute slug this generation belongs to."},"value":{"title":"Value","description":"The value held during this generation."},"active_from":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Active From","description":"When this value took effect."},"active_until":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Active Until","description":"When it was superseded. Null means it is still in force."},"actor_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Actor Id","description":"Opaque id of whoever set it."}},"type":"object","required":["attribute"],"title":"RecordHistoryEntry","description":"One generation of one attribute's value.\n\nValues are TEMPORAL rather than mutable: setting a new value closes the\nprevious generation and opens a new one, so history is the natural reading of\nthe store rather than a separate log that could drift from it. An entry with\na null `active_until` is the value currently in force."},"RecordHistoryResponse":{"properties":{"record_id":{"type":"string","title":"Record Id"},"entries":{"items":{"$ref":"#/components/schemas/RecordHistoryEntry"},"type":"array","title":"Entries"}},"type":"object","required":["record_id"],"title":"RecordHistoryResponse","description":"A record's value timeline, newest first."},"RecordListResponse":{"properties":{"records":{"items":{"$ref":"#/components/schemas/RecordResponse"},"type":"array","title":"Records"},"total":{"type":"integer","title":"Total"}},"type":"object","required":["records","total"],"title":"RecordListResponse","description":"Response for listing records."},"RecordMergeCascade":{"properties":{"relationships_repointed":{"type":"integer","title":"Relationships Repointed"},"relationships_deleted":{"type":"integer","title":"Relationships Deleted"},"associations_repointed":{"type":"integer","title":"Associations Repointed"},"associations_deleted":{"type":"integer","title":"Associations Deleted"}},"type":"object","required":["relationships_repointed","relationships_deleted","associations_repointed","associations_deleted"],"title":"RecordMergeCascade"},"RecordMergeFieldOverride":{"properties":{"attribute_slug":{"type":"string","title":"Attribute Slug"},"winner":{"type":"string","enum":["primary","secondary"],"title":"Winner"}},"type":"object","required":["attribute_slug","winner"],"title":"RecordMergeFieldOverride"},"RecordMergeRequest":{"properties":{"primary_record_id":{"type":"string","format":"uuid","title":"Primary Record Id"},"secondary_record_id":{"type":"string","format":"uuid","title":"Secondary Record Id"},"field_overrides":{"items":{"$ref":"#/components/schemas/RecordMergeFieldOverride"},"type":"array","title":"Field Overrides"},"expected_primary_revision":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Expected Primary Revision"},"expected_secondary_revision":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Expected Secondary Revision"}},"type":"object","required":["primary_record_id","secondary_record_id"],"title":"RecordMergeRequest","description":"Merge ``secondary_record_id`` into ``primary_record_id``. The primary's\ngraph8 identity (id, legacy_id/legacy_type) is preserved; the secondary is\narchived, never hard-deleted."},"RecordMergeResponse":{"properties":{"record":{"$ref":"#/components/schemas/RecordResponse"},"merge_history_id":{"type":"string","format":"uuid","title":"Merge History Id"},"cascade":{"$ref":"#/components/schemas/RecordMergeCascade"}},"type":"object","required":["record","merge_history_id","cascade"],"title":"RecordMergeResponse"},"RecordMutationEntry":{"properties":{"id":{"type":"string","title":"Id"},"action":{"type":"string","enum":["created","updated","archived","restored","recalculated"],"title":"Action"},"occurred_at":{"type":"string","format":"date-time","title":"Occurred At"},"revision":{"type":"integer","minimum":1.0,"title":"Revision"},"actor_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Actor Id"},"actor_type":{"type":"string","enum":["user","api","app","integration","system"],"title":"Actor Type"},"source":{"type":"string","title":"Source"},"app_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"App Id"},"changes":{"additionalProperties":{"$ref":"#/components/schemas/RecordMutationValueChange"},"type":"object","title":"Changes"},"was_archived":{"type":"boolean","title":"Was Archived"},"is_archived":{"type":"boolean","title":"Is Archived"}},"type":"object","required":["id","action","occurred_at","revision","actor_id","actor_type","source","changes","was_archived","is_archived"],"title":"RecordMutationEntry"},"RecordMutationValueChange":{"properties":{"before_present":{"type":"boolean","title":"Before Present"},"before":{"title":"Before"},"after_present":{"type":"boolean","title":"After Present"},"after":{"title":"After"}},"type":"object","required":["before_present","after_present"],"title":"RecordMutationValueChange"},"RecordMutationsResponse":{"properties":{"record_id":{"type":"string","title":"Record Id"},"entries":{"items":{"$ref":"#/components/schemas/RecordMutationEntry"},"type":"array","title":"Entries"},"next_cursor":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Next Cursor"}},"type":"object","required":["record_id","entries"],"title":"RecordMutationsResponse","description":"Immutable mutation facts, newest first, with a stable forward cursor."},"RecordNoteCreateRequest":{"properties":{"entity_type":{"type":"string","title":"Entity Type","description":"Record type the note is attached to.","default":""},"entity_id":{"type":"string","title":"Entity Id","description":"Id of that record.","default":""},"content":{"type":"string","title":"Content","description":"Note body."},"mentioned_users":{"items":{"$ref":"#/components/schemas/NoteMentionedUser"},"type":"array","title":"Mentioned Users","description":"Teammates mentioned in the note."},"records":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Records","description":"Further records to attach, each `{entity_type, entity_id}`."},"source_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Url","description":"Where the note was taken."}},"type":"object","required":["content"],"title":"RecordNoteCreateRequest","description":"Mirrors `GlobalNoteCreateRequest`."},"RecordProgressRequest":{"properties":{"record_ids":{"items":{"type":"string"},"type":"array","maxItems":500,"title":"Record Ids","description":"Records to report on. The app caps this at 500 and ignores the rest."}},"type":"object","title":"RecordProgressRequest","description":"Read in-flight per-record enrichment progress. A read, not a run."},"RecordRelationshipsResponse":{"properties":{"relationships":{"items":{"$ref":"#/components/schemas/RelatedRecordEdge"},"type":"array","title":"Relationships"},"next_offset":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Next Offset","description":"Next visible page offset; null at the end"}},"type":"object","required":["relationships","next_offset"],"title":"RecordRelationshipsResponse"},"RecordResponse":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"object_definition_id":{"type":"string","format":"uuid","title":"Object Definition Id"},"organization_id":{"type":"string","title":"Organization Id"},"is_archived":{"type":"boolean","title":"Is Archived"},"revision":{"type":"integer","minimum":1.0,"title":"Revision","default":1},"created_at":{"type":"string","format":"date-time","title":"Created At"},"updated_at":{"type":"string","format":"date-time","title":"Updated At"},"values":{"additionalProperties":true,"type":"object","title":"Values"}},"type":"object","required":["id","object_definition_id","organization_id","is_archived","created_at","updated_at","values"],"title":"RecordResponse","description":"Response for a record with its current attribute values."},"RecordRoleAssignRequest":{"properties":{"role_slot":{"type":"string","enum":["sdr","ae","csm"],"title":"Role Slot"},"user_id":{"type":"string","title":"User Id","description":"The org member to put in the slot."},"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason","description":"Why: manual_reassign | rule_based | account_owner_change | import | api.","default":"manual_reassign"}},"type":"object","required":["role_slot","user_id"],"title":"RecordRoleAssignRequest"},"RecordRolePayload":{"properties":{},"additionalProperties":true,"type":"object","title":"RecordRolePayload","description":"Role slots, their history, or the result of a change."},"RecordSyncPreviewRequest":{"properties":{"local_id":{"type":"string","title":"Local Id","description":"The record id."},"event_id":{"type":"string","format":"uuid","title":"Event Id"},"policy":{"anyOf":[{"$ref":"#/components/schemas/MashupSyncPolicy"},{"type":"null"}],"description":"Preview against this policy instead of the saved one."}},"type":"object","required":["local_id","event_id"],"title":"RecordSyncPreviewRequest","description":"Show what syncing one record would change, without changing it."},"RecordSyncRunRequest":{"properties":{"expected_version":{"type":"integer","minimum":1.0,"title":"Expected Version","description":"The policy version you read."}},"type":"object","required":["expected_version"],"title":"RecordSyncRunRequest","description":"Request a sync run now."},"RecordUpdateRequest":{"properties":{"values":{"additionalProperties":true,"type":"object","title":"Values","description":"Attribute values keyed by slug. Call `GET /objects/{object_slug}/attributes` for active fields. Canonical contacts and companies retain CONTACT_*, COMPANY_* and udo_* field names. Unknown keys are rejected with 422. PATCH preserves omitted fields; required fields cannot be cleared with null or an empty multivalue list. Record references must resolve to active records of their configured target object in the same organization and app."},"append_values":{"additionalProperties":{"items":{},"type":"array"},"type":"object","title":"Append Values","description":"Append canonical non-duplicate values to multivalue fields. Fields must not overlap values or remove_values."},"remove_values":{"additionalProperties":{"items":{},"type":"array"},"type":"object","title":"Remove Values","description":"Remove all canonical matches from multivalue fields. Fields must not overlap values or append_values."},"expected_revision":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Expected Revision","description":"Required for canonical contact or company PATCH. Apply only if the record still has this revision; otherwise return 409."}},"type":"object","title":"RecordUpdateRequest"},"RecordUpsertRequest":{"properties":{"values":{"additionalProperties":true,"type":"object","title":"Values","description":"Attribute values keyed by slug. Call `GET /objects/{object_slug}/attributes` for active fields. Canonical contacts and companies retain CONTACT_*, COMPANY_* and udo_* field names. Unknown keys are rejected with 422. PATCH preserves omitted fields; required fields cannot be cleared with null or an empty multivalue list. Record references must resolve to active records of their configured target object in the same organization and app."},"matching_attribute":{"type":"string","maxLength":100,"minLength":1,"pattern":"^[a-z][a-z0-9_]*$","title":"Matching Attribute","description":"Active single-value unique attribute. Its nonempty value must be supplied in values."},"expected_revision":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Expected Revision"}},"additionalProperties":false,"type":"object","required":["matching_attribute"],"title":"RecordUpsertRequest"},"RecordWriteRequest":{"properties":{"values":{"additionalProperties":true,"type":"object","title":"Values","description":"Attribute values keyed by slug. Call `GET /objects/{object_slug}/attributes` for active fields. Canonical contacts and companies retain CONTACT_*, COMPANY_* and udo_* field names. Unknown keys are rejected with 422. PATCH preserves omitted fields; required fields cannot be cleared with null or an empty multivalue list. Record references must resolve to active records of their configured target object in the same organization and app."}},"type":"object","title":"RecordWriteRequest","description":"A record payload: attribute slugs to values.\n\nUntyped by necessity — the valid keys and value shapes come from the\ncustomer's own attribute definitions at runtime. Every key is validated\nagainst those definitions before anything is written, and an unrecognised one\nis a 422 rather than a silent drop."},"RedialContactRequest":{"properties":{"contact_id":{"type":"string","title":"Contact Id"},"from_phone":{"type":"string","title":"From Phone"},"user_id":{"type":"string","title":"User Id"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id"},"campaign_builder_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Builder Campaign Id"},"session_id":{"type":"string","title":"Session Id"}},"type":"object","required":["contact_id","from_phone","user_id","session_id"],"title":"RedialContactRequest","description":"Mirrors `RedialContactRequest` minus `org_id`. CALLS THE CONTACT AGAIN."},"RedialState":{"properties":{"filters_snapshot":{"additionalProperties":true,"type":"object","title":"Filters Snapshot"},"last_contact_id":{"type":"integer","title":"Last Contact Id","default":0},"processed_count":{"type":"integer","title":"Processed Count","default":0},"started_at":{"type":"string","title":"Started At"}},"type":"object","required":["filters_snapshot","started_at"],"title":"RedialState","description":"Where a bulk redial sweep got to, so it can resume."},"RegenerateContextRequest":{"properties":{"website_url":{"type":"string","title":"Website Url","description":"Website to generate from. After a company-profile change this must be the NEW domain — intelligence is keyed by URL, so passing the old one silently regenerates the same stale content."},"doc_types":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Doc Types","description":"Specific Studio doc types to regenerate (e.g. ['icp_research','persona_research']). Omit to regenerate every document that already exists in the org."}},"type":"object","required":["website_url"],"title":"RegenerateContextRequest"},"RegenerateKeyRequest":{"properties":{"rotate_existing":{"type":"boolean","title":"Rotate Existing","description":"Acknowledge that the existing credential stops working IMMEDIATELY. Leave false to mint only when there is none.","default":false}},"type":"object","title":"RegenerateKeyRequest","description":"Mint a fresh ingest credential for a table."},"RegisterLibraryVideoAssetRequest":{"properties":{"org_video_id":{"type":"string","maxLength":64,"minLength":1,"title":"Org Video Id"}},"type":"object","required":["org_video_id"],"title":"RegisterLibraryVideoAssetRequest","description":"Pick a Studio library video (``cb_org_videos`` id) for a Video campaign."},"RegisterVideoAssetRequest":{"properties":{"key":{"type":"string","maxLength":512,"minLength":1,"title":"Key"},"title":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Title","default":""},"duration_s":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Duration S"},"width":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Width"},"height":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Height"},"source":{"type":"string","title":"Source","description":"upload | studio","default":"upload"}},"type":"object","required":["key"],"title":"RegisterVideoAssetRequest","description":"Register an object uploaded through /upload-url (the key it returned)."},"ReinstateSkip":{"properties":{"contact_id":{"type":"integer","title":"Contact Id"},"reason":{"type":"string","title":"Reason"}},"type":"object","required":["contact_id","reason"],"title":"ReinstateSkip"},"RejectDuplicateRequest":{"properties":{"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason"}},"type":"object","title":"RejectDuplicateRequest"},"RelatedRecordEdge":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"definition_id":{"type":"string","format":"uuid","title":"Definition Id"},"definition_revision":{"type":"integer","title":"Definition Revision"},"source_kind":{"type":"string","enum":["custom","contacts","companies","deals"],"title":"Source Kind"},"target_kind":{"type":"string","enum":["custom","contacts","companies","deals"],"title":"Target Kind"},"source_object_slug":{"type":"string","title":"Source Object Slug"},"target_object_slug":{"type":"string","title":"Target Object Slug"},"source_record_id":{"type":"string","title":"Source Record Id"},"target_record_id":{"type":"string","title":"Target Record Id"},"source_revision":{"type":"integer","title":"Source Revision"},"target_revision":{"type":"integer","title":"Target Revision"},"source_label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Label"},"target_label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Label"},"relationship_label":{"type":"string","title":"Relationship Label"},"can_unlink":{"type":"boolean","title":"Can Unlink"}},"type":"object","required":["id","definition_id","definition_revision","source_kind","target_kind","source_object_slug","target_object_slug","source_record_id","target_record_id","source_revision","target_revision","source_label","target_label","relationship_label","can_unlink"],"title":"RelatedRecordEdge"},"RelationshipChip":{"properties":{"record_id":{"type":"string","title":"Record Id"},"kind":{"type":"string","title":"Kind"},"object_slug":{"type":"string","title":"Object Slug"},"label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Label"}},"type":"object","required":["record_id","kind","object_slug","label"],"title":"RelationshipChip"},"RelationshipCreate":{"properties":{"definition_id":{"type":"string","format":"uuid","title":"Definition Id"},"target_record_id":{"type":"string","maxLength":255,"minLength":1,"title":"Target Record Id"},"expected_source_revision":{"type":"integer","exclusiveMinimum":0.0,"title":"Expected Source Revision"},"expected_target_revision":{"type":"integer","exclusiveMinimum":0.0,"title":"Expected Target Revision"},"expected_definition_revision":{"type":"integer","exclusiveMinimum":0.0,"title":"Expected Definition Revision"}},"additionalProperties":false,"type":"object","required":["definition_id","target_record_id","expected_source_revision","expected_target_revision","expected_definition_revision"],"title":"RelationshipCreate"},"RelationshipDefinitionCreate":{"properties":{"api_slug":{"type":"string","maxLength":100,"minLength":1,"pattern":"^[a-z][a-z0-9_]*$","title":"Api Slug"},"source_label":{"type":"string","maxLength":100,"minLength":1,"title":"Source Label"},"target_label":{"type":"string","maxLength":100,"minLength":1,"title":"Target Label"},"target":{"$ref":"#/components/schemas/RelationshipTarget"},"source_many":{"type":"boolean","title":"Source Many","default":true},"target_many":{"type":"boolean","title":"Target Many","default":true}},"additionalProperties":false,"type":"object","required":["api_slug","source_label","target_label","target"],"title":"RelationshipDefinitionCreate"},"RelationshipDefinitionListResponse":{"properties":{"relationships":{"items":{"$ref":"#/components/schemas/RelationshipDefinitionResponse"},"type":"array","title":"Relationships"},"total":{"type":"integer","title":"Total"}},"type":"object","required":["relationships","total"],"title":"RelationshipDefinitionListResponse"},"RelationshipDefinitionResponse":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"api_slug":{"type":"string","title":"Api Slug"},"source_kind":{"type":"string","title":"Source Kind"},"target_kind":{"type":"string","title":"Target Kind"},"source_object_definition_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Source Object Definition Id"},"target_object_definition_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Target Object Definition Id"},"source_label":{"type":"string","title":"Source Label"},"target_label":{"type":"string","title":"Target Label"},"source_many":{"type":"boolean","title":"Source Many"},"target_many":{"type":"boolean","title":"Target Many"},"revision":{"type":"integer","title":"Revision"},"is_archived":{"type":"boolean","title":"Is Archived"},"created_at":{"type":"string","format":"date-time","title":"Created At"}},"type":"object","required":["id","api_slug","source_kind","target_kind","source_object_definition_id","target_object_definition_id","source_label","target_label","source_many","target_many","revision","is_archived","created_at"],"title":"RelationshipDefinitionResponse"},"RelationshipGridCell":{"properties":{"records":{"items":{"$ref":"#/components/schemas/RelationshipChip"},"type":"array","title":"Records"},"total":{"type":"integer","title":"Total"}},"type":"object","required":["records","total"],"title":"RelationshipGridCell","description":"Up to ``GRID_CELL_CHIPS`` linked records plus how many the caller may see in\nall. Far ends the caller may not read contribute neither a chip nor the total."},"RelationshipGridCellsQuery":{"properties":{"record_ids":{"items":{"type":"string"},"type":"array","maxItems":100,"minItems":1,"title":"Record Ids"},"definition_ids":{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":10,"minItems":1,"title":"Definition Ids"}},"additionalProperties":false,"type":"object","required":["record_ids","definition_ids"],"title":"RelationshipGridCellsQuery","description":"Rows on screen (canonical ids: contact/company PK, deal UUID, or custom record\nUUID) and the relationship columns shown for them."},"RelationshipGridCellsResponse":{"properties":{"cells":{"additionalProperties":{"additionalProperties":{"$ref":"#/components/schemas/RelationshipGridCell"},"type":"object"},"type":"object","title":"Cells"}},"type":"object","required":["cells"],"title":"RelationshipGridCellsResponse","description":"``cells[record_id][definition_id]``. A row the caller may not see, or a column\nwhose far object the caller may not read, is absent rather than empty."},"RelationshipResponse":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"definition_id":{"type":"string","format":"uuid","title":"Definition Id"},"source_kind":{"type":"string","title":"Source Kind"},"source_record_id":{"type":"string","title":"Source Record Id"},"target_kind":{"type":"string","title":"Target Kind"},"target_record_id":{"type":"string","title":"Target Record Id"},"source_revision":{"type":"integer","title":"Source Revision"},"target_revision":{"type":"integer","title":"Target Revision"}},"type":"object","required":["id","definition_id","source_kind","source_record_id","target_kind","target_record_id","source_revision","target_revision"],"title":"RelationshipResponse"},"RelationshipTarget":{"properties":{"kind":{"type":"string","enum":["custom","contacts","companies","deals"],"title":"Kind"},"object_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Object Id"}},"additionalProperties":false,"type":"object","required":["kind"],"title":"RelationshipTarget"},"RelationshipTargetRow":{"properties":{"record_id":{"type":"string","title":"Record Id"},"kind":{"type":"string","title":"Kind"},"object_slug":{"type":"string","title":"Object Slug"},"label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Label"},"revision":{"type":"integer","title":"Revision"},"already_linked":{"type":"boolean","title":"Already Linked"},"can_link":{"type":"boolean","title":"Can Link"}},"type":"object","required":["record_id","kind","object_slug","label","revision","already_linked","can_link"],"title":"RelationshipTargetRow"},"RelationshipTargetsResponse":{"properties":{"records":{"items":{"$ref":"#/components/schemas/RelationshipTargetRow"},"type":"array","title":"Records"},"source_revision":{"type":"integer","title":"Source Revision"},"definition_revision":{"type":"integer","title":"Definition Revision"},"next_offset":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Next Offset"}},"type":"object","required":["records","source_revision","definition_revision","next_offset"],"title":"RelationshipTargetsResponse"},"ReleasePhoneRequest":{"properties":{"phone_number":{"type":"string","title":"Phone Number","description":"The number to release, E.164."},"provider":{"type":"string","enum":["twilio","telnyx"],"title":"Provider","description":"The carrier that holds it. It must match what the number was bought from - releasing a Telnyx number as `twilio` reaches the wrong provider."}},"type":"object","required":["phone_number","provider"],"title":"ReleasePhoneRequest","description":"Give a number back to the carrier. IRREVERSIBLE.\n\nMirrors `phone_numbers.interfaces.fastapi.dtos.ReleasePhoneRequest`."},"RemoveChannelsRequest":{"properties":{"channel_ids":{"items":{"type":"string"},"type":"array","minItems":1,"title":"Channel Ids","description":"Sequence-channel ids, from `GET .../channels`."}},"type":"object","required":["channel_ids"],"title":"RemoveChannelsRequest","description":"Detach senders from a sequence. Mirrors `BulkArchiveChannelParams`."},"RemoveContactsFromListRequest":{"properties":{"contact_ids":{"items":{"type":"integer"},"type":"array","title":"Contact Ids","description":"List of contact IDs to remove"}},"type":"object","required":["contact_ids"],"title":"RemoveContactsFromListRequest","description":"Request body for removing contacts from a list."},"RemovedStepSummary":{"properties":{"id":{"type":"string","title":"Id","description":"Step ID that was removed"},"step_order":{"type":"integer","title":"Step Order","description":"Position the step held before removal"},"step_type":{"type":"string","title":"Step Type","description":"Persisted step type, e.g. NETRION or HEYREACH"}},"type":"object","required":["id","step_order","step_type"],"title":"RemovedStepSummary","description":"One step removed by the LinkedIn-removal operation."},"RenameAIColumnRequest":{"properties":{"column_id":{"type":"string","title":"Column Id"},"name":{"type":"string","title":"Name"}},"type":"object","required":["column_id","name"],"title":"RenameAIColumnRequest","description":"Rename the column an AI group writes into. Display name only."},"RenderedStepContent":{"properties":{"subject":{"type":"string","title":"Subject","description":"Subject with spintax resolved to one variant"},"body":{"type":"string","title":"Body","description":"Body with spintax resolved to one variant"},"spintax_blocks":{"type":"integer","title":"Spintax Blocks","description":"Count of top-level spintax blocks across subject + body. 0 means this step contains no spintax at all, which distinguishes 'nothing to vary' from 'spintax failed to resolve'."},"total_combinations":{"type":"integer","title":"Total Combinations","description":"Distinct emails this step can produce. Always >= 1; a value of exactly 1 means the copy is too templated to vary, which is a legitimate outcome and not an error."},"variants":{"items":{"type":"string"},"type":"array","title":"Variants","description":"Up to 3 distinct body renderings under different selection seeds. This is the proof that spintax works: if these differ, per-contact variation is functioning. Fewer than 3 entries means the copy cannot produce more."},"variables_resolved":{"type":"boolean","title":"Variables Resolved","description":"False for this endpoint. Spintax is resolved but {{variables}} are left visible on purpose, because a preview has no contact and resolving against an empty contact would delete the token and show a hole in the copy. Variables fill in at send time.","default":false},"will_send_as_shown":{"type":"boolean","title":"Will Send As Shown","description":"True when the rendered copy above is what a recipient actually gets. False means content_issues contains errors that make the delivered email differ from this preview, because malformed tokens are silently DELETED at send rather than raising. Do not launch on a false.","default":true},"content_issues":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Content Issues","description":"Findings from the same content-syntax validator that blocks launch, so a caller sees them here instead of discovering them as a 400 on run (or worse, as missing text in a delivered email). Each entry carries code, severity, message, field and snippet. An error-severity entry will block POST /sequences/{id}/run."}},"type":"object","required":["subject","body","spintax_blocks","total_combinations"],"title":"RenderedStepContent","description":"What a step's copy actually looks like once spintax is resolved.\n\nExists because ``step_data`` is the stored TEMPLATE, not the delivered email.\nA caller reading raw ``{{a|b|c}}`` back out of a field called \"preview\" has no\nway to tell working spintax from broken spintax, which is precisely how a\nworking feature got reported as broken (see the PR that added this)."},"RepLimitsOverrideRequest":{"properties":{"max_contacts":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Max Contacts","description":"Null = explicitly unlimited."},"max_companies":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Max Companies","description":"Null = explicitly unlimited."},"monthly_credit_budget":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Monthly Credit Budget","description":"Null = explicitly unlimited."},"reset":{"type":"boolean","title":"Reset","description":"Delete the override; the role default applies again.","default":false}},"type":"object","title":"RepLimitsOverrideRequest"},"RepLimitsSettings":{"properties":{"max_contacts":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Max Contacts"},"max_companies":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Max Companies"},"conflict_company_owned":{"type":"string","enum":["allow","warn","block"],"title":"Conflict Company Owned","default":"allow"},"conflict_contact_active":{"type":"string","enum":["allow","warn","block"],"title":"Conflict Contact Active","default":"allow"},"reveal_policy":{"type":"string","enum":["within_limits","monthly_credit_budget","no_limit"],"title":"Reveal Policy","default":"no_limit"},"reveal_monthly_credit_budget":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Reveal Monthly Credit Budget"}},"type":"object","title":"RepLimitsSettings","description":"Per-role reveal/ownership limits. Mirrors `roles.RepLimitsSettings`.\n\nThe three `Literal`s are closed here rather than left as strings because\nthey reach the app's own `Literal` inside `_apply_rep_limits`."},"ReplaceHtmlRequest":{"properties":{"html":{"type":"string","maxLength":2000000,"title":"Html"},"edit_instruction":{"anyOf":[{"type":"string","maxLength":240},{"type":"null"}],"title":"Edit Instruction"}},"type":"object","required":["html"],"title":"ReplaceHtmlRequest","description":"Persist a whole-page HTML snapshot. Deterministic, spends nothing."},"RepoResponse":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"repo_url":{"type":"string","title":"Repo Url"},"repo_name":{"type":"string","title":"Repo Name"},"provider":{"type":"string","title":"Provider"},"default_branch":{"type":"string","title":"Default Branch"},"scan_status":{"type":"string","title":"Scan Status"},"install_status":{"type":"string","title":"Install Status"},"project_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Project Id"},"write_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Write Key"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["id","repo_url","repo_name","provider","default_branch","scan_status","install_status"],"title":"RepoResponse"},"ReportConfig":{"properties":{"filters":{"items":{"$ref":"#/components/schemas/ReportFilter"},"type":"array","maxItems":10,"title":"Filters"},"group_by":{"items":{"$ref":"#/components/schemas/ReportGroupBy"},"type":"array","maxItems":3,"title":"Group By"},"measures":{"items":{"$ref":"#/components/schemas/ReportMeasure"},"type":"array","maxItems":10,"title":"Measures"},"stage":{"anyOf":[{"$ref":"#/components/schemas/ReportStage"},{"type":"null"}]},"range":{"anyOf":[{"$ref":"#/components/schemas/ReportRange"},{"type":"null"}]},"timezone":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Timezone"}},"additionalProperties":false,"type":"object","title":"ReportConfig","description":"What a report computes. ``timezone`` (an IANA name) fixes how dates are bucketed and what \"end of day\" means;\nwhen absent the organization's time zone applies (never the server's)."},"ReportCreate":{"properties":{"title":{"type":"string","maxLength":200,"minLength":1,"title":"Title"},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description"},"object_slug":{"type":"string","maxLength":100,"minLength":1,"title":"Object Slug"},"chart_type":{"type":"string","enum":["table","bar","line","funnel","stage_over_time","time_in_stage"],"title":"Chart Type"},"config":{"$ref":"#/components/schemas/ReportConfig"},"visibility":{"type":"string","enum":["private","org"],"title":"Visibility","default":"private"}},"additionalProperties":false,"type":"object","required":["title","object_slug","chart_type","config"],"title":"ReportCreate"},"ReportDefinitionResponse":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"title":{"type":"string","title":"Title"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"source":{"$ref":"#/components/schemas/ReportSource"},"chart_type":{"type":"string","enum":["table","bar","line","funnel","stage_over_time","time_in_stage"],"title":"Chart Type"},"config":{"additionalProperties":true,"type":"object","title":"Config"},"visibility":{"type":"string","enum":["private","org"],"title":"Visibility"},"revision":{"type":"integer","title":"Revision"},"owner":{"$ref":"#/components/schemas/ReportOwner"},"is_owner":{"type":"boolean","title":"Is Owner"},"can_edit":{"type":"boolean","title":"Can Edit"},"can_delete":{"type":"boolean","title":"Can Delete"},"restricted":{"items":{"$ref":"#/components/schemas/RestrictedComponent"},"type":"array","title":"Restricted"},"restricted_count":{"type":"integer","title":"Restricted Count","default":0},"created_at":{"type":"string","format":"date-time","title":"Created At"},"updated_at":{"type":"string","format":"date-time","title":"Updated At"}},"type":"object","required":["id","title","source","chart_type","config","visibility","revision","owner","is_owner","can_edit","can_delete","created_at","updated_at"],"title":"ReportDefinitionResponse"},"ReportDraftAcceptRequest":{"properties":{"section_keys":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Section Keys"}},"type":"object","title":"ReportDraftAcceptRequest","description":"Which sections of the draft to apply (default: every section)."},"ReportFilter":{"properties":{"attribute_slug":{"type":"string","maxLength":100,"minLength":1,"title":"Attribute Slug"},"relationship_slug":{"anyOf":[{"type":"string","maxLength":100,"minLength":1},{"type":"null"}],"title":"Relationship Slug"},"operator":{"type":"string","enum":["eq","ne","gt","gte","lt","lte","contains","starts_with","is_null","is_not_null","in"],"title":"Operator"},"value":{"title":"Value"}},"additionalProperties":false,"type":"object","required":["attribute_slug","operator"],"title":"ReportFilter","description":"One filter on a field of the source, or (with ``relationship_slug``) on a field of the contact, company or deal\nthe source points at: the record passes when a linked record it may see matches. ``in`` is \"is any of\" and takes a\nlist of values."},"ReportGroupBy":{"properties":{"kind":{"type":"string","enum":["attribute","related_attribute","created_at"],"title":"Kind","default":"attribute"},"attribute_slug":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Attribute Slug"},"relationship_slug":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Relationship Slug"},"grain":{"anyOf":[{"type":"string","enum":["day","week","month","quarter","year"]},{"type":"null"}],"title":"Grain"}},"additionalProperties":false,"type":"object","title":"ReportGroupBy","description":"One group-by. ``attribute``: a field of the source (a date or timestamp field needs a ``grain``);\n``related_attribute``: a field of the ONE record a single-valued relationship points at; ``created_at``: the\nrecord's creation time, bucketed by ``grain``."},"ReportListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"ReportListPayload","description":"An OPEN envelope for a report that answers with a bare LIST.\n\nA bare list is reachable as `items`; a named list (`{\"counts\": {...}}`)\nkeeps its own key AND gains `items`, so a caller can read either shape\nwithout branching."},"ReportListResponse":{"properties":{"reports":{"items":{"$ref":"#/components/schemas/ReportDefinitionResponse"},"type":"array","title":"Reports"},"total":{"type":"integer","title":"Total"},"can_share":{"type":"boolean","title":"Can Share"}},"type":"object","required":["reports","total","can_share"],"title":"ReportListResponse"},"ReportMeasure":{"properties":{"kind":{"type":"string","enum":["count","sum","avg","min","max","related_count"],"title":"Kind"},"attribute_slug":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Attribute Slug"},"relationship_slug":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Relationship Slug"},"label":{"anyOf":[{"type":"string","maxLength":120,"minLength":1},{"type":"null"}],"title":"Label"}},"additionalProperties":false,"type":"object","required":["kind"],"title":"ReportMeasure","description":"One measure. ``count`` counts each record once (COUNT DISTINCT record id); ``sum`` / ``avg`` / ``min`` / ``max``\nread a numeric field's value; ``related_count`` counts the live records a relationship links each record to."},"ReportNativeField":{"properties":{"slug":{"type":"string","title":"Slug"},"title":{"type":"string","title":"Title"},"value_type":{"type":"string","enum":["text","number"],"title":"Value Type"},"operators":{"items":{"type":"string","enum":["eq","ne","gt","gte","lt","lte","contains","starts_with","is_null","is_not_null","in"]},"type":"array","title":"Operators"}},"type":"object","required":["slug","title","value_type","operators"],"title":"ReportNativeField","description":"One field of a contact, company or deal a report can group by or filter on through a relationship."},"ReportNativeFieldsResponse":{"properties":{"kinds":{"items":{"$ref":"#/components/schemas/ReportNativeKind"},"type":"array","title":"Kinds"}},"type":"object","required":["kinds"],"title":"ReportNativeFieldsResponse"},"ReportNativeKind":{"properties":{"kind":{"type":"string","enum":["contacts","companies","deals"],"title":"Kind"},"singular_noun":{"type":"string","title":"Singular Noun"},"plural_noun":{"type":"string","title":"Plural Noun"},"readable":{"type":"boolean","title":"Readable"},"fields":{"items":{"$ref":"#/components/schemas/ReportNativeField"},"type":"array","title":"Fields"}},"type":"object","required":["kind","singular_noun","plural_noun","readable","fields"],"title":"ReportNativeKind"},"ReportOwner":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"is_you":{"type":"boolean","title":"Is You","default":false}},"type":"object","title":"ReportOwner"},"ReportPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"ReportPayload","description":"An OPEN envelope around one report's answer.\n\nThe app wraps every one of these reports in `{success, data, meta}`, where\n`meta` carries the cache state, the window and - on the agency reports -\n`failed_org_ids`, the orgs that contributed NOTHING to the totals above.\nThat field is the difference between \"this client sent no email\" and \"we\ncould not query this client\", so it is forwarded rather than flattened\naway.\n\nOpen on purpose: `data` is `dict | list` in the app and its contents grow\nwith the product. A closed model would turn every new metric into a\nsilently dropped one."},"ReportPreview":{"properties":{"object_slug":{"type":"string","maxLength":100,"minLength":1,"title":"Object Slug"},"chart_type":{"type":"string","enum":["table","bar","line","funnel","stage_over_time","time_in_stage"],"title":"Chart Type"},"config":{"$ref":"#/components/schemas/ReportConfig"},"as_of":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"As Of"}},"additionalProperties":false,"type":"object","required":["object_slug","chart_type","config"],"title":"ReportPreview","description":"Run an unsaved report with the caller's own access (the builder's live preview). No drilldown."},"ReportRange":{"properties":{"from":{"type":"string","format":"date","title":"From"},"to":{"type":"string","format":"date","title":"To"},"grain":{"type":"string","enum":["day","week","month","quarter","year"],"title":"Grain","default":"month"}},"additionalProperties":false,"type":"object","required":["from","to"],"title":"ReportRange","description":"The calendar range a stage-over-time report snapshots, one column per ``grain`` period end (in the report's\ntime zone)."},"ReportResult":{"properties":{"kind":{"type":"string","const":"result","title":"Kind","default":"result"},"status":{"type":"string","enum":["ok","restricted"],"title":"Status","default":"ok"},"chart_type":{"type":"string","enum":["table","bar","line","funnel","stage_over_time","time_in_stage"],"title":"Chart Type"},"source":{"$ref":"#/components/schemas/ReportSource"},"timezone":{"type":"string","title":"Timezone"},"as_of":{"anyOf":[{"$ref":"#/components/schemas/AsOf"},{"type":"null"}]},"columns":{"items":{"$ref":"#/components/schemas/ResultColumn"},"type":"array","title":"Columns"},"rows":{"items":{"$ref":"#/components/schemas/ResultRow"},"type":"array","title":"Rows"},"totals":{"anyOf":[{"$ref":"#/components/schemas/ResultTotals"},{"type":"null"}]},"total_base_records":{"type":"integer","title":"Total Base Records","default":0},"total_groups":{"type":"integer","title":"Total Groups","default":0},"row_limit":{"type":"integer","title":"Row Limit","default":500},"truncated":{"type":"boolean","title":"Truncated","default":false},"chart_limit":{"type":"integer","title":"Chart Limit","default":20},"chart_truncated":{"type":"boolean","title":"Chart Truncated","default":false},"chart_other":{"anyOf":[{"$ref":"#/components/schemas/ChartOther"},{"type":"null"}]},"gaps":{"items":{"$ref":"#/components/schemas/GapNote"},"type":"array","title":"Gaps"},"restricted":{"items":{"$ref":"#/components/schemas/RestrictedComponent"},"type":"array","title":"Restricted"},"disclosures":{"items":{"type":"string"},"type":"array","title":"Disclosures"},"history_supported":{"type":"boolean","title":"History Supported","default":true}},"type":"object","required":["chart_type","source","timezone"],"title":"ReportResult"},"ReportRevisionRequest":{"properties":{"instruction":{"type":"string","maxLength":4000,"minLength":3,"title":"Instruction"}},"type":"object","required":["instruction"],"title":"ReportRevisionRequest","description":"The instruction for the AI rewrite of one research report."},"ReportRun":{"properties":{"as_of":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"As Of"},"drilldown":{"anyOf":[{"$ref":"#/components/schemas/DrilldownRequest"},{"type":"null"}]}},"additionalProperties":false,"type":"object","title":"ReportRun","description":"Run a saved report. ``as_of`` is a calendar date in the report's time zone (end of that day); absent = now."},"ReportRunApiResponse":{"properties":{"data":{"oneOf":[{"$ref":"#/components/schemas/ReportResult"},{"$ref":"#/components/schemas/DrilldownResult"}],"title":"Data","discriminator":{"propertyName":"kind","mapping":{"drilldown":"#/components/schemas/DrilldownResult","result":"#/components/schemas/ReportResult"}}},"pagination":{"anyOf":[{"$ref":"#/components/schemas/PaginationMeta"},{"type":"null"}]}},"type":"object","required":["data"],"title":"ReportRunApiResponse","description":"A report run: its result, or a page of the records behind a number when ``drilldown`` was asked (``data.kind``).\nNamed so the published schema is ``ReportRunApiResponse`` rather than a generated name of the union."},"ReportSource":{"properties":{"slug":{"type":"string","title":"Slug"},"singular_noun":{"type":"string","title":"Singular Noun"},"plural_noun":{"type":"string","title":"Plural Noun"},"kind":{"type":"string","enum":["object","process_list"],"title":"Kind"},"is_archived":{"type":"boolean","title":"Is Archived","default":false}},"type":"object","required":["slug","singular_noun","plural_noun","kind"],"title":"ReportSource"},"ReportStage":{"properties":{"attribute_slug":{"type":"string","maxLength":100,"minLength":1,"title":"Attribute Slug"},"order":{"items":{"type":"string"},"type":"array","maxItems":20,"minItems":2,"title":"Order"}},"additionalProperties":false,"type":"object","required":["attribute_slug","order"],"title":"ReportStage","description":"The stage field and the ORDERED stages a funnel, stage-over-time or time-in-stage report walks."},"ReportUpdate":{"properties":{"title":{"anyOf":[{"type":"string","maxLength":200,"minLength":1},{"type":"null"}],"title":"Title"},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description"},"chart_type":{"anyOf":[{"type":"string","enum":["table","bar","line","funnel","stage_over_time","time_in_stage"]},{"type":"null"}],"title":"Chart Type"},"config":{"anyOf":[{"$ref":"#/components/schemas/ReportConfig"},{"type":"null"}]},"visibility":{"anyOf":[{"type":"string","enum":["private","org"]},{"type":"null"}],"title":"Visibility"},"expected_revision":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Expected Revision"}},"additionalProperties":false,"type":"object","title":"ReportUpdate"},"RepurposeAdRequest":{"properties":{"source_type":{"type":"string","title":"Source Type"},"source_id":{"type":"string","title":"Source Id"},"platform":{"type":"string","title":"Platform","default":"linkedin"},"ad_format":{"type":"string","title":"Ad Format","default":"single_image"}},"type":"object","required":["source_type","source_id"],"title":"RepurposeAdRequest","description":"Derive an ad creative from an existing piece. SPENDS CREDIT."},"RepurposeSourceRequest":{"properties":{"source_type":{"type":"string","title":"Source Type"},"source_id":{"type":"string","title":"Source Id"}},"type":"object","required":["source_type","source_id"],"title":"RepurposeSourceRequest","description":"Derive a LinkedIn post from an existing piece. SPENDS CREDIT."},"RequestLogEntry":{"properties":{"request_id":{"type":"string","title":"Request Id","description":"Correlation id — matches the X-Request-Id response header"},"method":{"type":"string","title":"Method","description":"HTTP method"},"path":{"type":"string","title":"Path","description":"Request path"},"status":{"type":"integer","title":"Status","description":"HTTP status code of the response"},"timestamp":{"type":"integer","title":"Timestamp","description":"Unix seconds when the request completed"}},"type":"object","required":["request_id","method","path","status","timestamp"],"title":"RequestLogEntry"},"RequestRescheduleRequest":{"properties":{"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason"}},"type":"object","title":"RequestRescheduleRequest"},"RescheduleBookingRequest":{"properties":{"start_time":{"type":"string","title":"Start Time"},"rescheduling_reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Rescheduling Reason"}},"type":"object","required":["start_time"],"title":"RescheduleBookingRequest"},"ReserveSlotRequest":{"properties":{"event_type_id":{"type":"integer","title":"Event Type Id"},"slot_start":{"type":"string","title":"Slot Start","description":"ISO-8601 start of the slot being held."},"slot_end":{"type":"string","title":"Slot End","description":"ISO-8601 end of the slot being held."}},"type":"object","required":["event_type_id","slot_start","slot_end"],"title":"ReserveSlotRequest","description":"Hold a slot while a booker fills in the form.\n\nThe app types both times as bare strings and parses them with\n`datetime.fromisoformat` inside the handler with no guard, so a malformed\nvalue is an unhandled 500 there. They are validated as ISO-8601 here and\nforwarded unchanged."},"ReskinRequest":{"properties":{"swaps":{"items":{"$ref":"#/components/schemas/ColorSwap"},"type":"array","maxItems":8,"minItems":1,"title":"Swaps"}},"type":"object","required":["swaps"],"title":"ReskinRequest","description":"Swap the creative's palette. Deterministic, spends nothing."},"ResolveCompanyIdsRequest":{"properties":{"linkedin_company_ids":{"items":{"type":"integer"},"type":"array","title":"Linkedin Company Ids"}},"type":"object","title":"ResolveCompanyIdsRequest","description":"Turn LinkedIn company ids into graph8 company ids.\n\nThis is what makes a Hiring Signals result actionable: the search returns\nlcids, and a list or a sequence needs graph8 ids. The handler caps the\ninput server-side regardless of what is sent."},"ResolveThreadRequest":{"properties":{"resolution_note":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Resolution Note","description":"Why it was resolved."}},"type":"object","title":"ResolveThreadRequest","description":"Mark a discussion thread resolved.\n\nDistinct from completing the task: a task can be done with an unresolved\nthread and vice versa. Idempotent - re-resolving returns the existing row."},"ResponseRateDTO":{"properties":{"sent":{"type":"integer","title":"Sent"},"responded":{"type":"integer","title":"Responded"},"rate":{"type":"number","title":"Rate"}},"type":"object","required":["sent","responded","rate"],"title":"ResponseRateDTO"},"RestoreConflict":{"properties":{"section":{"type":"string","title":"Section"},"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"code":{"type":"string","title":"Code"},"field":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Field"},"why":{"type":"string","title":"Why","default":""},"fix":{"type":"string","title":"Fix","default":""}},"type":"object","required":["section","code"],"title":"RestoreConflict","description":"One receipt line: the refused item (section and id; for a field error the field slug), a stable code, why it was\nrefused and what fixes it. Never a value from the archive."},"RestoreCreate":{"properties":{"backup_id":{"type":"string","format":"uuid","title":"Backup Id"},"dry_run":{"type":"boolean","title":"Dry Run","description":"True (the default) writes nothing; send false to restore.","default":true}},"additionalProperties":false,"type":"object","required":["backup_id"],"title":"RestoreCreate","description":"Restore one completed backup of THIS workspace, by id. A record or report that is missing is added; one that\nexists is UPDATED to the backup's values where they differ, through the same checks as an edit (an archived record\nthe backup holds live is unarchived). Objects, fields, relationships, process lists, grants and links are only\nadded. Nothing that exists is ever deleted or archived.\n\n``dry_run`` defaults to true: every step and check runs and is rolled back, and the counts say exactly what a\nrestore would add, update and leave unchanged. A real restore must send ``dry_run: false``."},"RestoreJobListResponse":{"properties":{"restores":{"items":{"$ref":"#/components/schemas/RestoreJobResponse"},"type":"array","title":"Restores"},"total":{"type":"integer","title":"Total"},"limit":{"type":"integer","title":"Limit"},"offset":{"type":"integer","title":"Offset"}},"type":"object","required":["restores","total","limit","offset"],"title":"RestoreJobListResponse","description":"Restores, newest first (each without its receipt: read one restore for that)."},"RestoreJobResponse":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"backup_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Backup Id"},"status":{"type":"string","enum":["pending","running","completed","failed","expired"],"title":"Status"},"dry_run":{"type":"boolean","title":"Dry Run"},"scope":{"anyOf":[{"type":"string","enum":["complete","restricted"]},{"type":"null"}],"title":"Scope"},"counts":{"additionalProperties":{"$ref":"#/components/schemas/SectionCounts"},"type":"object","title":"Counts","description":"Per archive section. A dry run's counts are what the restore would do now."},"conflicts":{"items":{"$ref":"#/components/schemas/RestoreConflict"},"type":"array","title":"Conflicts","description":"One page of the receipt."},"conflict_count":{"type":"integer","title":"Conflict Count","default":0},"conflict_offset":{"type":"integer","title":"Conflict Offset","default":0},"conflicts_truncated":{"type":"boolean","title":"Conflicts Truncated","description":"More conflicts happened than the receipt keeps (the first 5,000); conflict_count is exact.","default":false},"error_code":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Error Code"},"created_at":{"type":"string","format":"date-time","title":"Created At"},"started_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Started At"},"completed_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Completed At"},"heartbeat_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Heartbeat At","description":"The run's last sign of life; while running, ``counts`` are its progress at that moment."},"totals":{"$ref":"#/components/schemas/SectionCounts","description":"``counts`` summed over every section."},"requested_by":{"anyOf":[{"$ref":"#/components/schemas/BackupRequester"},{"type":"null"}]},"note":{"type":"string","title":"Note","description":"What a restore adds, updates and never touches, in one sentence.","default":"Records and reports are matched by id: a missing one is added, and one that exists is updated to the backup's values where they differ (one archived now but live in the backup is unarchived). Objects, fields, relationships, process lists, grants and links are only added: one that exists is left as it is. Nothing that exists is deleted or archived, and calculated values are recomputed, never restored."}},"type":"object","required":["id","status","dry_run","created_at"],"title":"RestoreJobResponse"},"RestoreRevisionRequest":{"properties":{"index":{"type":"integer","minimum":0.0,"title":"Index"}},"type":"object","required":["index"],"title":"RestoreRevisionRequest","description":"Roll back to a snapshot. The restore is itself snapshotted first."},"RestrictedComponent":{"properties":{"id":{"type":"string","title":"Id"},"restricted":{"type":"boolean","const":true,"title":"Restricted","default":true}},"type":"object","required":["id"],"title":"RestrictedComponent","description":"A part of a report the viewer may not see. Hidden means ABSENT: it carries no title, no object name, no type and\nno reason, only its position id (``m0`` the first measure, ``g0`` the first group-by, ``f0`` the first filter,\n``stage`` the stage field), so a client can lock that slot in place."},"ResultColumn":{"properties":{"id":{"type":"string","title":"Id"},"kind":{"type":"string","enum":["group_by","measure","stage","gap"],"title":"Kind"},"label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Label"},"value_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Value Type"},"grain":{"anyOf":[{"type":"string","enum":["day","week","month","quarter","year"]},{"type":"null"}],"title":"Grain"},"restricted":{"type":"boolean","title":"Restricted","default":false}},"type":"object","required":["id","kind"],"title":"ResultColumn"},"ResultRow":{"properties":{"key":{"type":"string","title":"Key"},"group":{"items":{"$ref":"#/components/schemas/GroupValue"},"type":"array","title":"Group"},"measures":{"additionalProperties":{"anyOf":[{"type":"number"},{"type":"integer"},{"type":"null"}]},"type":"object","title":"Measures"},"record_count":{"type":"integer","title":"Record Count","default":0},"drilldown":{"oneOf":[{"$ref":"#/components/schemas/GroupTarget"},{"$ref":"#/components/schemas/StageTarget"},{"$ref":"#/components/schemas/SnapshotTarget"},{"$ref":"#/components/schemas/AllTarget"}],"title":"Drilldown","discriminator":{"propertyName":"kind","mapping":{"all":"#/components/schemas/AllTarget","group":"#/components/schemas/GroupTarget","snapshot":"#/components/schemas/SnapshotTarget","stage":"#/components/schemas/StageTarget"}}},"partial":{"type":"boolean","title":"Partial","default":false},"unstaged":{"additionalProperties":{"type":"integer"},"type":"object","title":"Unstaged"}},"type":"object","required":["key","drilldown"],"title":"ResultRow"},"ResultTotals":{"properties":{"record_count":{"type":"integer","title":"Record Count"},"measures":{"additionalProperties":{"anyOf":[{"type":"number"},{"type":"integer"},{"type":"null"}]},"type":"object","title":"Measures"}},"type":"object","required":["record_count"],"title":"ResultTotals"},"RetirementDecisionRequest":{"properties":{"short_code":{"type":"string","pattern":"^[A-HJ-NP-Za-hj-np-z2-9]{4}$","title":"Short Code","description":"The retirement's 4-character code."},"decision":{"type":"string","enum":["approved","rejected"],"title":"Decision"}},"type":"object","required":["short_code","decision"],"title":"RetirementDecisionRequest"},"RetirementUndoRequest":{"properties":{"short_code":{"type":"string","pattern":"^[A-HJ-NP-Za-hj-np-z2-9]{4}$","title":"Short Code","description":"The retirement's 4-character code."}},"type":"object","required":["short_code"],"title":"RetirementUndoRequest"},"RetryResearchReportRequest":{"properties":{"website_url":{"type":"string","title":"Website Url"},"report_type":{"type":"string","enum":["review_sentiment","competitive_teardown","voice_of_customer","gtm_channel","analyst_media","buyer_psychology"],"title":"Report Type"}},"type":"object","required":["website_url","report_type"],"title":"RetryResearchReportRequest","description":"Re-run one failed report. SPENDS CREDIT."},"RevenueAnalyticsPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"RevenueAnalyticsPayload","description":"A dashboard or rollup, as the app computes it."},"RevenuePlanCreateRequest":{"properties":{"name":{"type":"string","maxLength":255,"minLength":1,"title":"Name"},"slug":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Slug","description":"Derived from `name` when omitted."},"mrr_band":{"anyOf":[{"type":"string","enum":["<1k","1k-5k","5k-25k",">25k"]},{"type":"null"}],"title":"Mrr Band"},"list_price_cents":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"List Price Cents"}},"type":"object","required":["name"],"title":"RevenuePlanCreateRequest"},"RevenuePlanUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":255,"minLength":1},{"type":"null"}],"title":"Name"},"slug":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Slug"},"mrr_band":{"anyOf":[{"type":"string","enum":["<1k","1k-5k","5k-25k",">25k"]},{"type":"null"}],"title":"Mrr Band"},"list_price_cents":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"List Price Cents"},"active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Active"}},"type":"object","title":"RevenuePlanUpdateRequest"},"RevenueRecordListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"RevenueRecordListPayload","description":"A list result under `items`."},"RevenueRecordPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"RevenueRecordPayload","description":"An activity, snapshot, plan or result, as the app returns it."},"Reversal":{"properties":{"event_id":{"type":"string","maxLength":200,"minLength":1,"title":"Event Id"},"amount":{"anyOf":[{"type":"number","exclusiveMinimum":0.0},{"type":"string"}],"title":"Amount"},"evidence":{"type":"string","maxLength":4000,"minLength":1,"title":"Evidence"}},"additionalProperties":false,"type":"object","required":["event_id","amount","evidence"],"title":"Reversal"},"ReviewRequest":{"properties":{"local_id":{"type":"string","title":"Local Id","description":"The record, as an exact decimal string."},"event_id":{"type":"string","format":"uuid","title":"Event Id"},"policy":{"type":"null","title":"Policy","description":"Always null on a review; the stored policy applies."},"expected_version":{"type":"integer","minimum":1.0,"title":"Expected Version"},"action":{"type":"string","enum":["retry","preserve"],"title":"Action","description":"`retry` re-applies the change; `preserve` keeps the record as it is."}},"additionalProperties":false,"type":"object","required":["local_id","event_id","expected_version","action"],"title":"ReviewRequest","description":"Resolve one flagged record-sync change."},"RewriteFieldRequest":{"properties":{"field":{"type":"string","maxLength":64,"title":"Field"},"instruction":{"type":"string","maxLength":2000,"title":"Instruction"}},"type":"object","required":["field","instruction"],"title":"RewriteFieldRequest","description":"Rewrite ONE copy field with AI. SPENDS CREDIT."},"RewriteTextRequest":{"properties":{"element_id":{"type":"string","maxLength":200,"title":"Element Id"},"instruction":{"type":"string","maxLength":2000,"title":"Instruction","description":"What to change, in plain words."}},"type":"object","required":["element_id","instruction"],"title":"RewriteTextRequest","description":"Rewrite ONE element with an AI instruction. THIS SPENDS AI CREDIT."},"RivalAttachRequest":{"properties":{"competitor_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Competitor Id","description":"The competitor. Null detaches the current one."},"status":{"type":"string","title":"Status","description":"Where the deal stands against them."}},"type":"object","required":["status"],"title":"RivalAttachRequest","description":"Record which competitor is on a deal, and how it is going."},"RoleCreateRequest":{"properties":{"name":{"type":"string","maxLength":100,"minLength":1,"title":"Name"},"slug":{"type":"string","maxLength":50,"minLength":1,"pattern":"^[a-z][a-z0-9_-]*$","title":"Slug"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"permissions":{"items":{"type":"string"},"type":"array","title":"Permissions"},"manages_role_slugs":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Manages Role Slugs"},"rep_limits":{"anyOf":[{"$ref":"#/components/schemas/RepLimitsSettings"},{"type":"null"}]}},"type":"object","required":["name","slug"],"title":"RoleCreateRequest","description":"Define a new role. Mirrors `roles.RoleCreateRequest`.\n\n`permissions` is bounded by the app's own non-escalation guard\n(`_assert_can_grant_permissions`): a caller may not mint a role granting a\npermission they do not themselves hold. That guard runs INSIDE the handler\nand is deliberately not duplicated here - see the router docstring."},"RoleUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":100,"minLength":1},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"permissions":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Permissions"},"manages_role_slugs":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Manages Role Slugs"},"rep_limits":{"anyOf":[{"$ref":"#/components/schemas/RepLimitsSettings"},{"type":"null"}]}},"type":"object","title":"RoleUpdateRequest","description":"Replace a role's definition. Mirrors `roles.RoleUpdateRequest`.\n\n`permissions` is a REPLACEMENT, not a merge, and it takes effect for\neveryone who already holds the role. That is why the operation is tiered\n`destructive` rather than `write`."},"RoutingFormCondition":{"properties":{"field_id":{"type":"string","minLength":1,"title":"Field Id"},"operator":{"type":"string","enum":["equals","not_equals","contains","not_contains","is_empty","is_not_empty","greater_than","less_than","select_equals","select_not_equals"],"title":"Operator"},"value":{"type":"string","title":"Value","default":""}},"type":"object","required":["field_id","operator"],"title":"RoutingFormCondition"},"RoutingFormField":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"label":{"type":"string","maxLength":500,"minLength":1,"title":"Label"},"identifier":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Identifier"},"type":{"type":"string","enum":["text","email","phone","number","textarea","select","multiselect","radio","checkbox"],"title":"Type","default":"select"},"placeholder":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Placeholder"},"required":{"type":"boolean","title":"Required","default":true},"options":{"items":{"$ref":"#/components/schemas/RoutingFormFieldOption"},"type":"array","title":"Options"}},"type":"object","required":["label"],"title":"RoutingFormField"},"RoutingFormFieldOption":{"properties":{"label":{"type":"string","maxLength":500,"minLength":1,"title":"Label"},"value":{"type":"string","maxLength":500,"minLength":1,"title":"Value"},"event_type_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Event Type Id"}},"type":"object","required":["label","value"],"title":"RoutingFormFieldOption"},"RoutingFormRouteInput":{"properties":{"conditions":{"items":{"$ref":"#/components/schemas/RoutingFormCondition"},"type":"array","title":"Conditions"},"action_type":{"type":"string","enum":["redirect_event_type","redirect_url","show_message"],"title":"Action Type","default":"redirect_event_type"},"action_value":{"type":"string","title":"Action Value","default":""},"is_fallback":{"type":"boolean","title":"Is Fallback","default":false},"position":{"type":"integer","title":"Position","default":0}},"type":"object","title":"RoutingFormRouteInput"},"RowFieldValues":{"properties":{"record_id":{"type":"integer","title":"Record Id","description":"Contact ID (entity='contacts') or company ID (entity='companies')."},"fields":{"items":{"$ref":"#/components/schemas/FieldValueItem"},"type":"array","maxItems":500,"title":"Fields","description":"Column/value pairs to write on this row. Empty = no-op (counts as ok with 0 writes)."}},"type":"object","required":["record_id"],"title":"RowFieldValues","description":"One row (contact or company) plus the columns to set on it."},"Rule":{"properties":{"name":{"type":"string","maxLength":120,"minLength":1,"title":"Name"},"target":{"type":"string","enum":["default","group","product"],"title":"Target","default":"default"},"product_ids":{"items":{"type":"string"},"type":"array","maxItems":500,"title":"Product Ids"},"stages":{"items":{"$ref":"#/components/schemas/Stage"},"type":"array","maxItems":60,"minItems":1,"title":"Stages"}},"additionalProperties":false,"type":"object","required":["name","stages"],"title":"Rule"},"RunAIEnrichRequest":{"properties":{"group_id":{"type":"string","title":"Group Id","description":"group_id of a saved AI enrichment config (starts with 'ai_enrich')"},"list_id":{"type":"integer","title":"List Id","description":"List ID the records belong to"},"record_ids":{"items":{"type":"integer"},"type":"array","title":"Record Ids","description":"Contact IDs to enrich"},"max_records":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Max Records","description":"Optional cap on records processed (defaults to len(record_ids))."},"skip_existing_values":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Skip Existing Values","description":"Override the config's skip_existing_values setting."}},"type":"object","required":["group_id","list_id","record_ids"],"title":"RunAIEnrichRequest","description":"Run a saved AI enrichment config on specific records.\n\nThe prompt, model, outputs, and column mapping live on the config\nreferenced by `group_id`. We accept `record_ids` so callers can target\nexactly the contacts they want enriched."},"RunBuiltinScraperRequest":{"properties":{"prompt":{"type":"string","maxLength":5000,"minLength":10,"title":"Prompt"},"max_results":{"type":"integer","maximum":2000.0,"minimum":10.0,"title":"Max Results","default":200},"model":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Model"},"auto_enrich":{"type":"boolean","title":"Auto Enrich","description":"Also enrich each scraped row. Charged on top.","default":false},"approved_max_credits":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Approved Max Credits"},"quote_expires_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Quote Expires At"}},"type":"object","required":["prompt"],"title":"RunBuiltinScraperRequest","description":"Describe what to collect; the scraper fills the table. CHARGES.\n\nThe price is quoted by `GET /workbench/scraper/credit-estimate`. A quote is\napproved by passing `approved_max_credits` and `quote_expires_at` back."},"RunDetectionRequest":{"properties":{"entity_type":{"type":"string","enum":["contact","company","deal"],"title":"Entity Type","description":"What to scan."}},"type":"object","required":["entity_type"],"title":"RunDetectionRequest","description":"Mirrors `duplicates.interfaces.router._RunDetectionRequest`."},"RunFindPeopleRequest":{"properties":{"enrichment_mode":{"type":"string","enum":["first_10","all_rows","selected"],"title":"Enrichment Mode"},"record_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Record Ids","description":"Required for `selected`."}},"type":"object","required":["enrichment_mode"],"title":"RunFindPeopleRequest","description":"Which companies a find-people config runs over."},"RunFormulaRequest":{"properties":{"record_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Record Ids"},"visible_record_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Visible Record Ids"},"context_record_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Context Record Ids"},"mode":{"anyOf":[{"type":"string","enum":["selected","visible","empty"]},{"type":"null"}],"title":"Mode"},"max_records":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Max Records"},"batch_size":{"type":"integer","maximum":1000.0,"minimum":1.0,"title":"Batch Size","default":10},"dry_run":{"type":"boolean","title":"Dry Run","description":"Validate only; write nothing.","default":false}},"type":"object","title":"RunFormulaRequest","description":"Which records a formula column is computed for.\n\nWith no ids and no `mode`, the formula runs over the list's records up to\n`max_records`. `mode: empty` fills only records whose value is blank."},"RunProviderScraperRequest":{"properties":{"preset_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Preset Id"},"custom_actor_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Custom Actor Id"},"input_config":{"additionalProperties":true,"type":"object","title":"Input Config"},"max_results":{"type":"integer","maximum":50000.0,"minimum":1.0,"title":"Max Results","default":1000},"auto_enrich":{"type":"boolean","title":"Auto Enrich","default":true},"approved_max_credits":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Approved Max Credits"},"quote_expires_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Quote Expires At"}},"type":"object","title":"RunProviderScraperRequest","description":"Run a scraper on your connected provider account. CHARGES per result.\n\nOne of `preset_id` (from `GET /workbench/scraper/presets`) or\n`custom_actor_id`. `auto_enrich` DEFAULTS TO TRUE here: every result is\nalso enriched, and charged, unless you turn it off."},"RunQualificationRequest":{"properties":{"template_id":{"type":"string","format":"uuid","title":"Template Id"},"list_id":{"type":"integer","title":"List Id"},"usecase":{"anyOf":[{"type":"string","enum":["web-research","create-modify-content"]},{"type":"null"}],"title":"Usecase"},"requalify":{"type":"boolean","title":"Requalify","description":"Re-run records that already have a verdict.","default":false}},"type":"object","required":["template_id","list_id"],"title":"RunQualificationRequest","description":"Qualify a list against a template."},"RunRecordWorkflowRequest":{"properties":{"list_id":{"type":"integer","title":"List Id","description":"List (workbench) the workflow belongs to."},"workflow_id":{"type":"string","title":"Workflow Id","description":"Workflow to run."},"record_ids":{"items":{"type":"integer"},"type":"array","title":"Record Ids","description":"Rows to run it on, for `selected`."},"run_mode":{"type":"string","enum":["selected","filtered","all"],"title":"Run Mode","description":"Which rows to run on.","default":"selected"}},"type":"object","required":["list_id","workflow_id","record_ids"],"title":"RunRecordWorkflowRequest","description":"Mirrors `RunWorkflowRequest`. `run_mode` is closed to the app's three values."},"RunStagingAIRequest":{"properties":{"row_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Row Ids","description":"Rows to run. OMIT to run EVERY row in the table."},"exclude_row_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array","maxItems":100000},{"type":"null"}],"title":"Exclude Row Ids"},"model":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Model","description":"Override the configured model."},"prompt":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Prompt","description":"Override the configured prompt."},"status_filter":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status Filter"},"conditions":{"anyOf":[{"items":{"additionalProperties":{"type":"string"},"type":"object"},"type":"array"},{"type":"null"}],"title":"Conditions"},"qualification_mode":{"type":"boolean","title":"Qualification Mode","default":false},"multi_row_output":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Multi Row Output"},"max_rows_per_source":{"anyOf":[{"type":"integer","maximum":50.0,"minimum":1.0},{"type":"null"}],"title":"Max Rows Per Source"},"approved_max_credits":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Approved Max Credits","description":"Ceiling the caller approves. The run refuses to exceed it."},"quote_expires_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Quote Expires At"},"quote_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Quote Id"}},"type":"object","title":"RunStagingAIRequest","description":"Which rows a run covers, and the spend the caller approved.\n\nOMITTING `row_ids` RUNS EVERY ROW. `exclude_row_ids` narrows that back down."},"RunWaterfallEnrichRequest":{"properties":{"column_id":{"type":"string","title":"Column Id","description":"column_id from a saved waterfall pipeline"},"list_id":{"type":"integer","title":"List Id","description":"List ID the records belong to"},"record_ids":{"items":{"type":"integer"},"type":"array","title":"Record Ids","description":"Contact IDs to enrich"},"skip_existing_values":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Skip Existing Values","description":"Override the pipeline's skip_existing_values setting. If None (default), the pipeline's saved setting is used."}},"type":"object","required":["column_id","list_id","record_ids"],"title":"RunWaterfallEnrichRequest","description":"Run a saved waterfall pipeline on specific records."},"RunWorkbenchFindPeopleRequest":{"properties":{"row_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Row Ids"},"exclude_row_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array","maxItems":100000},{"type":"null"}],"title":"Exclude Row Ids"},"enrichment_mode":{"type":"string","enum":["first_10","all_rows","selected"],"title":"Enrichment Mode","default":"all_rows"}},"type":"object","title":"RunWorkbenchFindPeopleRequest","description":"Which rows find-people runs over.\n\n`selected` requires `row_ids` or `exclude_row_ids`; the other modes forbid\nthem."},"SAMLConfigRequest":{"properties":{"provider_name":{"type":"string","title":"Provider Name","description":"IdP name: okta, azure, google, onelogin, custom."},"idp_entity_id":{"type":"string","title":"Idp Entity Id","description":"Identity Provider Entity ID."},"idp_sso_url":{"type":"string","title":"Idp Sso Url","description":"SSO URL from the IdP."},"idp_certificate":{"type":"string","title":"Idp Certificate","description":"X.509 certificate from the IdP, PEM format."},"require_sso":{"type":"boolean","title":"Require Sso","description":"Make SSO the ONLY way in. False here and set it later with `PUT /org/sso/enforcement` once you have signed in through SSO yourself — that ordering is what stops a lockout.","default":false},"allowed_domains":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Allowed Domains","description":"Email domains allowed to sign in this way."}},"type":"object","required":["provider_name","idp_entity_id","idp_sso_url","idp_certificate"],"title":"SAMLConfigRequest","description":"SAML sign-in configuration.\n\nThe certificate and URLs come from the identity provider. Nothing here is\nguessable, which is why every one of the first four fields is required —\na half-configured SSO that then gets activated is how an org locks itself\nout."},"SDRAnalyticsMeta":{"properties":{"org_id":{"type":"string","title":"Org Id"},"days":{"type":"integer","title":"Days"},"cached":{"type":"boolean","title":"Cached"},"stale":{"type":"boolean","title":"Stale","default":false},"cache_ttl":{"type":"integer","title":"Cache Ttl","default":60},"timestamp":{"type":"string","format":"date-time","title":"Timestamp"},"query_time_ms":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Query Time Ms"}},"type":"object","required":["org_id","days","cached","timestamp"],"title":"SDRAnalyticsMeta","description":"Metadata for SDR analytics responses."},"SDRAnalyticsResponse":{"properties":{"success":{"type":"boolean","title":"Success","default":true},"data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"items":{},"type":"array"}],"title":"Data"},"meta":{"$ref":"#/components/schemas/SDRAnalyticsMeta"}},"type":"object","required":["data","meta"],"title":"SDRAnalyticsResponse","description":"Standard SDR analytics response wrapper."},"SandboxStatusResponse":{"properties":{"sandbox":{"type":"boolean","title":"Sandbox","default":true},"environment":{"type":"string","title":"Environment","description":"Which graph8 deployment answered: 'sandbox' (developer sandbox), 'qa' (the QA environment) or 'live' (production).","default":"sandbox"},"org_id":{"type":"string","title":"Org Id"},"message":{"type":"string","title":"Message"},"key_mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Key Mode","description":"Mode of the API key that made the call: 'live', 'test' or 'sandbox'."}},"type":"object","required":["org_id","message"],"title":"SandboxStatusResponse"},"SaveAIConfigRequest":{"properties":{"config":{"$ref":"#/components/schemas/AIEnrichmentConfigDto"},"run_immediately":{"type":"boolean","const":false,"title":"Run Immediately","description":"Always false. Saving never runs - the app refuses immediate execution so a save can never become an unpriced spend.","default":false},"target_records":{"anyOf":[{"items":{"type":"string","format":"uuid"},"type":"array"},{"type":"null"}],"title":"Target Records"}},"type":"object","required":["config"],"title":"SaveAIConfigRequest","description":"Save an AI enrichment group. Saving costs nothing; running it does."},"SaveColumnAIConfigRequest":{"properties":{"prompt":{"type":"string","minLength":1,"title":"Prompt"},"model":{"type":"string","title":"Model","default":"openai/gpt-4o"},"usecase":{"type":"string","enum":["content_generation","web-research"],"title":"Usecase","default":"content_generation"},"conditions":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Conditions","description":"Only run the pass on rows matching these conditions."}},"type":"object","required":["prompt"],"title":"SaveColumnAIConfigRequest","description":"Configure ONE column's AI pass. Saving costs nothing; running does."},"SaveConnectionRequest":{"properties":{"connection_id":{"type":"string","title":"Connection Id","description":"The id the OAuth flow returned."},"provider":{"type":"string","title":"Provider","description":"Stable graph8 provider name."},"provider_config_key":{"type":"string","title":"Provider Config Key","description":"Provider config key."},"connection_config":{"additionalProperties":{"type":"string"},"type":"object","title":"Connection Config","description":"Provider-specific configuration captured during the flow."}},"type":"object","required":["connection_id","provider","provider_config_key"],"title":"SaveConnectionRequest","description":"Record a connection the OAuth flow has already established.\n\nThis does NOT perform the OAuth handshake - the hosted flow does that, and\nthis stores its result. `connection_id` is the id that flow handed back,\nnot one you choose."},"SaveIntentToMetadataRequest":{"properties":{"force_update":{"type":"boolean","title":"Force Update","description":"Overwrite intent metadata already on a contact, rather than only filling gaps.","default":false}},"type":"object","title":"SaveIntentToMetadataRequest","description":"Write each contact's resolved intent onto the contact record.\n\nNo `org_id`: the org is the authenticated key's own."},"SaveListPipelineRequest":{"properties":{"name":{"type":"string","maxLength":255,"minLength":1,"title":"Name"},"steps":{"items":{"$ref":"#/components/schemas/ListPipelineStep"},"type":"array","maxItems":20,"minItems":1,"title":"Steps"},"enabled":{"type":"boolean","title":"Enabled","default":false}},"type":"object","required":["name","steps"],"title":"SaveListPipelineRequest","description":"Create a list pipeline.\n\n`enabled: true` ARMS it: an enabled pipeline runs its steps over the list,\nand every enrichment step charges."},"SaveSearchRequest":{"properties":{"title":{"type":"string","maxLength":255,"minLength":1,"title":"Title"},"scope":{"type":"string","maxLength":64,"minLength":1,"title":"Scope","description":"What the saved search is over - `contacts` or `companies` today. Deliberately a free string rather than a closed enum, matching the app, which is designed to add more."},"icp_query":{"additionalProperties":true,"type":"object","title":"Icp Query","description":"The search itself. Opaque and round-tripped as-is."},"id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Id","description":"Send the id of an existing saved search to REPLACE it."}},"additionalProperties":false,"type":"object","required":["title","scope","icp_query"],"title":"SaveSearchRequest","description":"Store a search so a person can run it again later.\n\n`icp_query` is OPAQUE and round-tripped verbatim: the app stores it as a\nplain JSON blob and does not interpret it at save time, so this contract\ndoes not either. That is also why it is the one place here that does not\ngo through the field map - translating a blob nobody reads would change\nwhat the caller gets back.\n\n`id` present means UPDATE the saved search rather than create a new one."},"SaveSkillResultRequest":{"properties":{"execution_id":{"type":"string","title":"Execution Id","description":"The skill execution that produced the content."},"action_name":{"type":"string","title":"Action Name","description":"Action within that execution."},"content":{"type":"string","title":"Content","description":"Document body to store."}},"type":"object","required":["execution_id","action_name","content"],"title":"SaveSkillResultRequest","description":"Attach the output of a skill run to a record as a document."},"SaveStagingAIConfigRequest":{"properties":{"prompt":{"type":"string","minLength":1,"title":"Prompt"},"model":{"type":"string","title":"Model","default":"openai/gpt-4o"},"usecase":{"type":"string","title":"Usecase","default":"content_generation"},"output_columns":{"items":{"$ref":"#/components/schemas/OutputColumnDef"},"type":"array","title":"Output Columns"},"entity_type":{"anyOf":[{"type":"string","enum":["contact","company"]},{"type":"null"}],"title":"Entity Type"},"multi_row_output":{"type":"boolean","title":"Multi Row Output","default":false},"max_rows_per_source":{"type":"integer","maximum":50.0,"minimum":1.0,"title":"Max Rows Per Source","default":50}},"type":"object","required":["prompt"],"title":"SaveStagingAIConfigRequest","description":"Configure the table-level AI pass. Saving costs nothing; running does."},"SaveWaterfallRequest":{"properties":{"config":{"$ref":"#/components/schemas/WaterfallConfig"},"run_immediately":{"type":"boolean","title":"Run Immediately","description":"Ignored on a workbench table.","default":false},"target_records":{"anyOf":[{"items":{"type":"string","format":"uuid"},"type":"array"},{"type":"null"}],"title":"Target Records","description":"Ignored on a workbench table."}},"type":"object","required":["config"],"title":"SaveWaterfallRequest","description":"Create or overwrite a workbench waterfall column.\n\n`run_immediately` and `target_records` are carried for parity with the app\nmodel and IGNORED by the workbench save: saving never runs anything. Run it\nwith `POST /workbench/tables/{table_id}/waterfall/configs/{column_id}/run`."},"SavedViewCreateRequest":{"properties":{"name":{"type":"string","minLength":1,"title":"Name","description":"Display name."},"queue":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Queue"},"filters":{"additionalProperties":true,"type":"object","title":"Filters","description":"Filter set to restore."},"shared":{"type":"boolean","title":"Shared","description":"Visible to teammates when true.","default":false},"icon":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Icon"}},"type":"object","required":["name"],"title":"SavedViewCreateRequest","description":"A named queue + filter combination."},"SavedViewResponse":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"entity_type":{"$ref":"#/components/schemas/EntityType"},"context_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Context Key"},"is_reusable":{"type":"boolean","title":"Is Reusable"},"is_default":{"type":"boolean","title":"Is Default"},"visibility":{"$ref":"#/components/schemas/Visibility"},"title":{"type":"string","title":"Title"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"state":{"additionalProperties":true,"type":"object","title":"State"},"created_by":{"type":"string","title":"Created By"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated At"},"is_owner":{"type":"boolean","title":"Is Owner"}},"type":"object","required":["id","entity_type","context_key","is_reusable","is_default","visibility","title","description","state","created_by","created_at","updated_at","is_owner"],"title":"SavedViewResponse","description":"Response shape — flat shape with state at top level for convenience."},"ScanConfigDTO":{"properties":{"mode":{"type":"string","enum":["auto","manual"],"title":"Mode","default":"auto"},"include_paths":{"items":{"type":"string","maxLength":255},"type":"array","maxItems":50,"title":"Include Paths"}},"type":"object","title":"ScanConfigDTO","description":"Per-competitor page-selection config (persisted on profile.meta.scan_config).\n\nmode=auto: Firecrawl /map → rank by traffic + pricing/feature paths → scrape\ntop N (= tier page budget). mode=manual: scrape include_paths (literal or\n/wildcard/* patterns), capped to the budget."},"ScanResponse":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"repo_id":{"type":"string","format":"uuid","title":"Repo Id"},"tech_stack":{"additionalProperties":true,"type":"object","title":"Tech Stack"},"api_routes":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Api Routes"},"readme_summary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Readme Summary"},"product_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Product Type"},"gtm_readiness":{"additionalProperties":true,"type":"object","title":"Gtm Readiness","default":{}},"scan_duration_ms":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Scan Duration Ms"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"}},"type":"object","required":["id","repo_id","tech_stack","api_routes"],"title":"ScanResponse"},"ScanResultsRequest":{"properties":{"tech_stack":{"additionalProperties":true,"type":"object","title":"Tech Stack","description":"Detected tech stack (framework, language, etc.)"},"api_routes":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Api Routes","description":"Detected API routes","default":[]},"readme_summary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Readme Summary","description":"Extracted README summary"},"product_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Product Type","description":"Detected product type (b2b_saas, api, etc.)"},"gtm_readiness":{"additionalProperties":true,"type":"object","title":"Gtm Readiness","description":"GTM readiness flags","default":{}},"scan_duration_ms":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Scan Duration Ms","description":"Scan duration in milliseconds"}},"type":"object","required":["tech_stack"],"title":"ScanResultsRequest"},"ScheduleBuyDomainCheckRequest":{"properties":{"names":{"items":{"type":"string"},"type":"array","maxItems":100,"minItems":1,"title":"Names","description":"Domain names to validate"}},"type":"object","required":["names"],"title":"ScheduleBuyDomainCheckRequest","description":"Validate edited candidate names: owned-by-you, and available. SPENDS NOTHING."},"ScheduleBuyDomainSuggestRequest":{"properties":{"count":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Count","description":"How many candidate names to return"},"domain_tld":{"type":"string","title":"Domain Tld","description":"Extension to generate against, e.g. '.com'","default":".com"},"offset":{"type":"integer","maximum":1000.0,"minimum":0.0,"title":"Offset","description":"Rotate the generator to get fresh candidates","default":0},"roots":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":10},{"type":"null"}],"title":"Roots","description":"Word roots to build names from"},"pattern":{"anyOf":[{"type":"string","enum":["prefix","suffix","both"]},{"type":"null"}],"title":"Pattern","description":"Where to attach the root"},"tlds":{"anyOf":[{"items":{"type":"string"},"type":"array","minItems":1},{"type":"null"}],"title":"Tlds","description":"Restrict to these extensions"},"avoid":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":50},{"type":"null"}],"title":"Avoid","description":"Names to exclude"}},"type":"object","required":["count"],"title":"ScheduleBuyDomainSuggestRequest","description":"Preview the domain names a plan WOULD buy. SPENDS NOTHING."},"ScheduleBuyPlanRequest":{"properties":{"target_monthly_volume":{"type":"integer","maximum":100000000.0,"minimum":0.0,"title":"Target Monthly Volume","description":"Contacts you intend to reach per month"},"idle_mailboxes_snapshot":{"type":"integer","minimum":0.0,"title":"Idle Mailboxes Snapshot","description":"Idle mailboxes you already hold, from /suggest"},"warmup_provider":{"type":"string","enum":["warmy","instantly","smartlead"],"title":"Warmup Provider","description":"Warmup engine the bought mailboxes are enrolled with","default":"warmy"},"domain_tld":{"type":"string","title":"Domain Tld","description":"Extension to buy, e.g. '.com'","default":".com"},"registrants":{"items":{"additionalProperties":true,"type":"object"},"type":"array","maxItems":20,"title":"Registrants","description":"Not accepted for new plans. Use persona_ids."},"mailbox_aliases":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Mailbox Aliases","description":"Not accepted for new plans. Use persona_ids."},"persona_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array","maxItems":20},{"type":"null"}],"title":"Persona Ids","description":"Sender identity IDs. At least one is required to start a schedule."},"workspace_uid":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Workspace Uid","description":"Existing provisioning workspace to reuse"},"daily_send_cap":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Daily Send Cap","description":"Sends per mailbox per day","default":15},"sending_days_per_month":{"type":"integer","maximum":31.0,"minimum":1.0,"title":"Sending Days Per Month","description":"Sending days assumed per month","default":22},"mailboxes_per_domain":{"type":"integer","maximum":5.0,"minimum":1.0,"title":"Mailboxes Per Domain","description":"Mailboxes bought on each domain","default":3},"domains_per_batch":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Domains Per Batch","description":"Domains bought per daily batch","default":10},"reuse_domains":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":500,"minItems":1},{"type":"null"}],"title":"Reuse Domains","description":"Adopt these owned domains instead of buying. Each must have fewer live mailboxes than mailboxes_per_domain; the plan tops it up and holds credits for exactly the missing ones"},"domain_names":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":500,"minItems":1},{"type":"null"}],"title":"Domain Names","description":"Approved names to buy, in order"}},"type":"object","required":["target_monthly_volume","idle_mailboxes_snapshot"],"title":"ScheduleBuyPlanRequest","description":"Create and LOCK a staggered buying plan. PLACES REAL CREDIT HOLDS.\n\nMirrors the app's ``CreatePlanRequest`` field for field, including the\nrule that new plans require ``persona_ids``. Manual ``registrants`` /\n``mailbox_aliases`` are still parsed so a legacy payload 422s here\nrather than inside the proxy."},"ScheduleBuySuggestRequest":{"properties":{"target_monthly_volume":{"type":"integer","maximum":100000000.0,"minimum":0.0,"title":"Target Monthly Volume","description":"Contacts you intend to reach per month"},"daily_send_cap":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Daily Send Cap","description":"Sends per mailbox per day","default":15},"sending_days_per_month":{"type":"integer","maximum":31.0,"minimum":1.0,"title":"Sending Days Per Month","description":"Sending days assumed per month","default":22},"mailboxes_per_domain":{"type":"integer","maximum":5.0,"minimum":1.0,"title":"Mailboxes Per Domain","description":"Mailboxes bought on each domain","default":3},"domains_per_batch":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Domains Per Batch","description":"Domains bought per daily batch","default":10},"reuse_domain_count":{"anyOf":[{"type":"integer","maximum":500.0,"minimum":1.0},{"type":"null"}],"title":"Reuse Domain Count","description":"Price a REUSE plan over this many owned domains instead"},"reuse_missing_mailboxes":{"anyOf":[{"type":"integer","maximum":2500.0,"minimum":1.0},{"type":"null"}],"title":"Reuse Missing Mailboxes","description":"With reuse_domain_count: the total mailboxes those domains are missing (each domain: mailboxes_per_domain minus its live mailboxes). Omitted, every domain is priced as empty"}},"type":"object","required":["target_monthly_volume"],"title":"ScheduleBuySuggestRequest","description":"Size a plan for a target volume: idle capacity, net-new domains and mailboxes, credit cost.\nSPENDS NOTHING. Mirrors the app's `SuggestRequest` field for field."},"ScheduleConfigRequest":{"properties":{"action_type":{"type":"string","enum":["run_ai","run_formula","crm_import"],"title":"Action Type"},"cron_expression":{"anyOf":[{"type":"string","maxLength":100,"minLength":5},{"type":"null"}],"title":"Cron Expression"},"frequency":{"anyOf":[{"type":"string","enum":["hourly","daily","weekly"]},{"type":"null"}],"title":"Frequency"},"action_config":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Action Config"},"enabled":{"type":"boolean","title":"Enabled","default":false}},"type":"object","required":["action_type"],"title":"ScheduleConfigRequest","description":"Run something on this table on a schedule.\n\nA schedule whose `action_type` is `run_ai` SPENDS CREDITS on every firing,\nwithout a further call. `enabled` defaults to false so creating one is not\nthe same act as starting it."},"ScheduleDayWindow":{"properties":{"day":{"type":"string","title":"Day","description":"Lowercase day name: monday | tuesday | wednesday | thursday | friday | saturday | sunday."},"start":{"type":"string","title":"Start","description":"Window start, 24h HH:MM in `timezone`."},"end":{"type":"string","title":"End","description":"Window end, 24h HH:MM in `timezone`."}},"type":"object","required":["day","start","end"],"title":"ScheduleDayWindow","description":"One day's send window — flattens `{start, end}` from the sequencer.\n\nDays that are absent from the underlying config (= no sending) are\nomitted from the response rather than serialized as nulls — keeps\nthe response compact and matches the picker UI's behaviour."},"ScheduleListItem":{"properties":{"id":{"type":"string","title":"Id","description":"Schedule UUID; pass back to launch / PATCH endpoints."},"name":{"type":"string","title":"Name","description":"Display name as set in the Sequencer schedule UI."},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Optional human description."},"timezone":{"type":"string","title":"Timezone","description":"IANA timezone name applied to every window (e.g. 'Europe/Madrid')."},"windows":{"items":{"$ref":"#/components/schemas/ScheduleDayWindow"},"type":"array","title":"Windows","description":"Per-day send windows for the schedule. Days with no window are omitted."},"is_archived":{"type":"boolean","title":"Is Archived","description":"Archived schedules are excluded by default — pass `include_archived=true` to include them.","default":false}},"type":"object","required":["id","name","timezone"],"title":"ScheduleListItem","description":"One row in the schedule picker. `id` feeds `schedule_id` on the launch body."},"SchedulePlanPersonasRequest":{"properties":{"persona_ids":{"items":{"type":"integer","exclusiveMinimum":0.0},"type":"array","maxItems":20,"minItems":1,"title":"Persona Ids"}},"type":"object","required":["persona_ids"],"title":"SchedulePlanPersonasRequest","description":"Personas to ADD to a persona-mode plan. Add-only: there is no removal."},"ScheduleRequest":{"properties":{"planned_publish_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Planned Publish At"},"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id"},"clear_planned":{"type":"boolean","title":"Clear Planned","default":false},"arm":{"type":"boolean","title":"Arm","description":"TRUE MEANS IT WILL PUBLISH ITSELF at planned_publish_at, with no further human step. False only records the date.","default":false},"publish_settings":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Publish Settings"}},"type":"object","title":"ScheduleRequest","description":"Place a piece on the calendar, or ARM it to publish itself.\n\n`arm` is the consequential field: false plans the date for a human, true\nhands it to the publish sweep, which will put the piece in front of real\npeople at `planned_publish_at` with no further confirmation."},"SchedulesListResponse":{"properties":{"data":{"items":{"$ref":"#/components/schemas/ScheduleListItem"},"type":"array","title":"Data"}},"type":"object","required":["data"],"title":"SchedulesListResponse","description":"Envelope for `GET /schedules`."},"SchedulingListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"SchedulingListPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape.\n\nA named list (`{\"events\": [...]}`) keeps its own key AND gains `items`, so\na generic client can page any of these the same way."},"SchedulingPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"SchedulingPayload","description":"An open envelope for a filter, a setting, an embed config or a slot grid.\n\nOpen because org settings gain branding fields as the booking page does\nand the embed config gains styling keys as the widget does. Closing it\nwould drop a field the app had already started returning."},"SchemaVersionResponse":{"properties":{"schema_version_id":{"type":"string","title":"Schema Version Id"},"app_id":{"type":"string","title":"App Id"},"version":{"type":"integer","title":"Version","description":"Human-facing ordinal. Nothing keys on it; the digest is the identity."},"digest":{"type":"string","title":"Digest","description":"SHA-256 of the canonical schema. Re-publishing the same schema resolves here."},"status":{"type":"string","title":"Status"},"manifest":{"additionalProperties":true,"type":"object","title":"Manifest","description":"The stored canonical schema. Self-describing, so the version needs no other source."},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"published_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Published At"},"deprecated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Deprecated At"}},"type":"object","required":["schema_version_id","app_id","version","digest","status"],"title":"SchemaVersionResponse","description":"One published (or draft) object-schema version."},"ScopeCatalogEntry":{"properties":{"scope":{"type":"string","title":"Scope"},"action":{"type":"string","title":"Action"},"default":{"type":"boolean","title":"Default"},"strict":{"type":"boolean","title":"Strict"}},"type":"object","required":["scope","action","default","strict"],"title":"ScopeCatalogEntry"},"ScopeCatalogResource":{"properties":{"resource":{"type":"string","title":"Resource"},"scopes":{"items":{"$ref":"#/components/schemas/ScopeCatalogEntry"},"type":"array","title":"Scopes"}},"type":"object","required":["resource","scopes"],"title":"ScopeCatalogResource"},"ScopeCatalogResponse":{"properties":{"resources":{"items":{"$ref":"#/components/schemas/ScopeCatalogResource"},"type":"array","title":"Resources"},"default_scopes":{"items":{"type":"string"},"type":"array","title":"Default Scopes"},"read_only_scopes":{"items":{"type":"string"},"type":"array","title":"Read Only Scopes","description":"The read-only preset: every ':read' scope in the grantable vocabulary. Minting a key with exactly these produces a credential that can look but never write, run, launch or delete — the 'read-only key' standard option (issue #21188)."},"full_access_scopes":{"items":{"type":"string"},"type":"array","title":"Full Access Scopes","description":"The full-access preset: every grantable scope except the explicit-only strict ones. `default_scopes` is read-only, so this is what a creator picks to opt in to write/run/launch/delete."},"total":{"type":"integer","title":"Total"}},"type":"object","required":["resources","default_scopes","total"],"title":"ScopeCatalogResponse"},"ScrapeConfigUpdateRequest":{"properties":{"exclude_paths":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Exclude Paths","description":"URL path patterns to skip while crawling."},"max_pages":{"anyOf":[{"type":"integer","maximum":5000.0,"minimum":10.0},{"type":"null"}],"title":"Max Pages","description":"Pages per crawl. The app's own bounds."},"include_blog_pages":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Include Blog Pages"}},"type":"object","title":"ScrapeConfigUpdateRequest","description":"Change how the org crawls. Only what you send is written."},"ScrapeSourceCreateRequest":{"properties":{"url":{"type":"string","maxLength":2000,"minLength":4,"title":"Url","description":"Root URL. Everything under it is followed."},"frequency":{"type":"string","enum":["daily","weekly","monthly","manual"],"title":"Frequency","description":"How often to re-crawl. `manual` never re-crawls.","default":"weekly"},"max_pages":{"type":"integer","maximum":1000.0,"minimum":10.0,"title":"Max Pages","description":"Ceiling, not a target - a small site only crawls what exists.","default":500}},"type":"object","required":["url"],"title":"ScrapeSourceCreateRequest","description":"A site to crawl into a collection on a schedule.\n\nCREATING ONE CRAWLS IMMEDIATELY - it does not wait for the first scheduled\nrun. That is why this operation is `billable` rather than a plain write."},"ScrapeSourceUpdateRequest":{"properties":{"frequency":{"anyOf":[{"type":"string","enum":["daily","weekly","monthly","manual"]},{"type":"null"}],"title":"Frequency"},"enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Enabled","description":"False pauses the recurring crawl; the source survives."},"max_pages":{"anyOf":[{"type":"integer","maximum":1000.0,"minimum":10.0},{"type":"null"}],"title":"Max Pages"}},"type":"object","title":"ScrapeSourceUpdateRequest","description":"Change a source's cadence, page ceiling, or pause it. Omitted = unchanged."},"ScraperConnectionRequest":{"properties":{"api_key":{"type":"string","minLength":1,"title":"Api Key","description":"Your provider API token. Never returned."},"configuration":{"additionalProperties":true,"type":"object","title":"Configuration"}},"type":"object","required":["api_key"],"title":"ScraperConnectionRequest","description":"Connect your own scraper provider account. The token is write-only."},"ScraperConnectionTestRequest":{"properties":{"api_key":{"type":"string","minLength":1,"title":"Api Key"}},"type":"object","required":["api_key"],"title":"ScraperConnectionTestRequest","description":"Check a token against the provider without saving it."},"SdrDialerTargetsRequest":{"properties":{"sdr_email":{"type":"string","title":"Sdr Email"},"daily_dials_target":{"type":"integer","minimum":0.0,"title":"Daily Dials Target"},"daily_meetings_target":{"type":"integer","minimum":0.0,"title":"Daily Meetings Target"},"updated_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated By"}},"type":"object","required":["sdr_email","daily_dials_target","daily_meetings_target"],"title":"SdrDialerTargetsRequest","description":"One rep's daily goals, overriding the org default."},"SearchCompanyItem":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain"},"website":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Website"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"industry":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Industry"},"industry_group":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Industry Group"},"employee_count":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Employee Count"},"revenue":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Revenue"},"founded_year":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Founded Year"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone"},"address":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Address"},"city":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"City"},"state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"State"},"country":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country"},"zip":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Zip"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url"},"linkedin_followers":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Followers"},"facebook_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Facebook Url"},"twitter_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Twitter Url"},"crunchbase_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Crunchbase Url"},"logo_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Logo Url"}},"type":"object","title":"SearchCompanyItem","description":"Company result from open data search."},"SearchContactItem":{"properties":{"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"middle_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Middle Name"},"work_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Work Email"},"personal_emails":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Personal Emails"},"direct_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Direct Phone"},"mobile_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mobile Phone"},"job_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Title"},"job_department":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Department"},"seniority_level":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Seniority Level"},"role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Role"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url"},"linkedin_headline":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Headline"},"city":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"City"},"state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"State"},"country":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country"},"company_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Name"},"company_domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Domain"},"company_industry":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Industry"},"company_employee_count":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Employee Count"},"company_country":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Country"},"confidence_score":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Confidence Score"},"locked_fields":{"items":{"type":"string"},"type":"array","title":"Locked Fields","description":"Fields whose value exists but is locked (shown as \"***\") until the contact is added to a list. A null field has no value."}},"type":"object","title":"SearchContactItem","description":"Contact result from open data search."},"SearchCountVariant":{"properties":{"key":{"type":"string","maxLength":128,"minLength":1,"title":"Key","description":"Your name for this variant, e.g. the chip left out."},"filters":{"items":{"$ref":"#/components/schemas/SearchFilter"},"type":"array","title":"Filters","description":"The filter conditions (AND logic)."}},"type":"object","required":["key"],"title":"SearchCountVariant","description":"One filter set to count: the search as it would run, in the public field vocabulary."},"SearchCountVariantsPayload":{"properties":{"counts":{"additionalProperties":{"anyOf":[{"type":"integer"},{"type":"null"}]},"type":"object","title":"Counts","description":"Variant key to match count; null when it failed or timed out."},"at_least":{"items":{"type":"string"},"type":"array","title":"At Least","description":"Keys whose count is a lower bound (show `10,000+`)."},"skipped":{"items":{"type":"string"},"type":"array","title":"Skipped","description":"Keys not counted: over the variant, condition or value limit."}},"type":"object","required":["counts"],"title":"SearchCountVariantsPayload","description":"Match counts per variant key."},"SearchCountVariantsRequest":{"properties":{"variants":{"items":{"$ref":"#/components/schemas/SearchCountVariant"},"type":"array","minItems":1,"title":"Variants","description":"Any number is accepted: the first 16 are counted and the keys of the rest come back in `skipped`."}},"type":"object","required":["variants"],"title":"SearchCountVariantsRequest","description":"Count how many records several filter sets match. Nothing is returned but counts."},"SearchDiscoveryPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"SearchDiscoveryPayload","description":"An open envelope for an autocomplete or filter-option result."},"SearchFilter":{"properties":{"field":{"type":"string","title":"Field","description":"Field name to filter on (e.g., 'job_title', 'country', 'industry')"},"operator":{"$ref":"#/components/schemas/SearchOperator","description":"Filter operator"},"value":{"items":{},"type":"array","title":"Value","description":"Filter values"}},"type":"object","required":["field","operator"],"title":"SearchFilter","description":"A single filter condition."},"SearchFilterDto":{"properties":{"field":{"type":"string","title":"Field"},"operator":{"type":"string","title":"Operator"},"value":{"items":{},"type":"array","title":"Value"}},"type":"object","required":["field","operator"],"title":"SearchFilterDto","description":"One people-search condition."},"SearchImportPreviewRequest":{"properties":{"filters":{"items":{"additionalProperties":true,"type":"object"},"type":"array","minItems":1,"title":"Filters"},"sample_size":{"type":"integer","maximum":1000.0,"minimum":1.0,"title":"Sample Size","default":50},"max_result":{"anyOf":[{"type":"integer","maximum":50000.0,"minimum":1.0},{"type":"null"}],"title":"Max Result"},"max_employees_per_company":{"anyOf":[{"type":"integer","maximum":1000.0,"minimum":1.0},{"type":"null"}],"title":"Max Employees Per Company"}},"type":"object","required":["filters"],"title":"SearchImportPreviewRequest","description":"Sample what a people search would import. Contact details stay masked."},"SearchImportRequest":{"properties":{"contacts":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Contacts","description":"Contacts to import directly."},"icp_filters":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Icp Filters","description":"Import EVERYTHING these filters match, up to `max_result`. The unbounded form of this operation."},"max_result":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Max Result"},"max_employees_per_company":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Max Employees Per Company"},"destination_list_id":{"type":"integer","title":"Destination List Id"},"source_list_id":{"type":"integer","title":"Source List Id"},"source_companies":{"items":{"$ref":"#/components/schemas/SourceCompanyDto"},"type":"array","title":"Source Companies"}},"type":"object","required":["destination_list_id","source_list_id"],"title":"SearchImportRequest","description":"Import people directly, either a given set or everything an ICP query matches."},"SearchOperator":{"type":"string","enum":["any_of","contains","all_of","none_of","is_empty","is_not_empty","between","exists"],"title":"SearchOperator","description":"Supported filter operators for search queries."},"SearchPostEngagementsRequest":{"properties":{"platform":{"type":"string","enum":["x","linkedin","reddit","instagram","youtube"],"title":"Platform","default":"x"},"engagement_type":{"anyOf":[{"type":"string","enum":["comment","reaction"]},{"type":"null"}],"title":"Engagement Type"},"page":{"type":"integer","minimum":1.0,"title":"Page","default":1},"limit":{"type":"integer","maximum":200.0,"minimum":1.0,"title":"Limit","default":100}},"type":"object","title":"SearchPostEngagementsRequest","description":"Filters over engagements ALREADY stored against a post."},"SearchPostsRequest":{"properties":{"conditions":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Conditions","description":"Grid-style filter expressions, passed through unchanged. Their grammar is the app's, not this contract's - a typed model here would freeze a filter language that still moves."},"page":{"type":"integer","minimum":1.0,"title":"Page","default":1},"limit":{"type":"integer","maximum":200.0,"minimum":1.0,"title":"Limit","default":100},"listener_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Listener Id"},"platform":{"anyOf":[{"type":"string","enum":["x","linkedin","reddit","instagram","youtube"]},{"type":"null"}],"title":"Platform"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"`new`, `reviewed` or `dismissed`."},"min_score":{"anyOf":[{"type":"number","maximum":1.0,"minimum":0.0},{"type":"null"}],"title":"Min Score"},"max_score":{"anyOf":[{"type":"number","maximum":1.0,"minimum":0.0},{"type":"null"}],"title":"Max Score"},"since":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Since"},"until":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Until"},"has_contact":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Has Contact","description":"Only posts whose author resolved to a graph8 contact."},"hide_low_confidence":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Hide Low Confidence","description":"Hide posts the classifier scored confidently LOW (< 0.5), while keeping never-classified ones visible. Not the same as `min_score=0.5`, which would also hide the unscored."}},"type":"object","title":"SearchPostsRequest","description":"Filters over posts ALREADY matched and stored. Fetches nothing live."},"SearchRequest":{"properties":{"filters":{"items":{"$ref":"#/components/schemas/SearchFilter"},"type":"array","title":"Filters","description":"Filter conditions (AND logic)"},"page":{"type":"integer","minimum":1.0,"title":"Page","description":"Page number (1-indexed). page * limit may not exceed 10,000 (the paging window); narrow the filters to reach records beyond it.","default":1},"limit":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Limit","description":"Results per page (max 100)","default":25}},"type":"object","title":"SearchRequest","description":"Request body for search endpoints."},"SearchResearchPreviewRequest":{"properties":{"lead_prompt":{"type":"string","minLength":1,"title":"Lead Prompt"},"sample_size":{"type":"integer","maximum":1000.0,"minimum":1.0,"title":"Sample Size","default":50},"max_result":{"anyOf":[{"type":"integer","maximum":50000.0,"minimum":1.0},{"type":"null"}],"title":"Max Result"},"max_employees_per_company":{"anyOf":[{"type":"integer","maximum":1000.0,"minimum":1.0},{"type":"null"}],"title":"Max Employees Per Company"}},"type":"object","required":["lead_prompt"],"title":"SearchResearchPreviewRequest","description":"Describe your leads in words; a model writes the search filters."},"SearchSaveRequest":{"properties":{"filters":{"items":{"$ref":"#/components/schemas/SearchFilter"},"type":"array","title":"Filters","description":"Filter conditions (AND logic)"},"page":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Page","description":"Page number (1-indexed)","default":1},"limit":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Limit","description":"Results per page (max 100)","default":25},"list_title":{"type":"string","title":"List Title","description":"Title for the new list"},"max_results":{"type":"integer","maximum":10000.0,"minimum":1.0,"title":"Max Results","description":"Maximum results to save (max 10,000)","default":1000}},"type":"object","required":["list_title"],"title":"SearchSaveRequest","description":"Request to search and save results to a list."},"SearchSaveResponse":{"properties":{"list_id":{"type":"integer","title":"List Id"},"list_title":{"type":"string","title":"List Title"},"estimated_total":{"type":"integer","title":"Estimated Total"},"status":{"type":"string","title":"Status","default":"processing"}},"type":"object","required":["list_id","list_title","estimated_total"],"title":"SearchSaveResponse","description":"Response from save-to-list endpoints."},"SearchSignalFilter":{"properties":{"type":{"type":"string","enum":["hiring","tech","company_type","describes","lookalike","new_in_role"],"title":"Type"},"negate":{"type":"boolean","title":"Negate","description":"Match companies WITHOUT the signal (hiring, tech, company_type).","default":false},"roles":{"items":{"type":"string"},"type":"array","title":"Roles","description":"hiring: role titles."},"days":{"type":"integer","maximum":730.0,"minimum":1.0,"title":"Days","description":"hiring / new_in_role: look-back window.","default":30},"status":{"type":"string","enum":["new","open"],"title":"Status","default":"new"},"min_roles":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Min Roles","default":1},"exclude_staffing":{"type":"boolean","title":"Exclude Staffing","default":true},"techs":{"items":{"type":"string"},"type":"array","title":"Techs","description":"tech: technologies."},"match":{"type":"string","enum":["any","all"],"title":"Match","default":"any"},"categories":{"items":{"type":"string"},"type":"array","title":"Categories","description":"company_type: category ids."},"text":{"type":"string","title":"Text","description":"describes: what the companies do.","default":""},"facet":{"type":"string","enum":["what","sells","serves"],"title":"Facet","default":"what"},"domains":{"items":{"type":"string"},"type":"array","title":"Domains","description":"lookalike: seed company domains."},"top_k":{"type":"integer","maximum":5000.0,"minimum":10.0,"title":"Top K","default":300}},"type":"object","required":["type"],"title":"SearchSignalFilter","description":"One signal. Which list must be non-empty depends on `type`."},"SectionCounts":{"properties":{"created":{"type":"integer","title":"Created","description":"Not in the workspace by id: added.","default":0},"updated":{"type":"integer","title":"Updated","description":"In the workspace by id with other values: written back to the backup's values (records and reports only; every other section is only added, so this stays 0 there).","default":0},"unchanged":{"type":"integer","title":"Unchanged","description":"In the workspace by id and left exactly as it is: it already holds the backup's values, or its section is only added.","default":0},"conflicts":{"type":"integer","title":"Conflicts","default":0},"skipped":{"type":"integer","title":"Skipped","description":"Not restored by design (e.g. schema from a restricted archive).","default":0}},"type":"object","title":"SectionCounts","description":"What a restore did (or, for a dry run, would do) with one archive section. Every row of the section is counted\nexactly once: ``created + updated + unchanged + conflicts + skipped`` is the section's rows in the backup."},"SectionLibraryRebuildRequest":{"properties":{"page_urls":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Page Urls","description":"Replace the automatic page selection with exactly these pages."},"extra_page_urls":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Extra Page Urls","description":"Add these pages to whatever the picker chose."}},"type":"object","title":"SectionLibraryRebuildRequest","description":"Mirrors `RebuildSectionLibraryRequest`.\n\nThe two lists are NOT interchangeable: `page_urls` REPLACES the automatic\npage selection, `extra_page_urls` ADDS to it. Sending the first is how you\noverride the picker; sending the second is how you top it up."},"SectionTagOverride":{"properties":{"custom":{"items":{"type":"string"},"type":"array","title":"Custom","description":"Tags added to this section."},"hidden":{"items":{"type":"string"},"type":"array","title":"Hidden","description":"Auto-derived tags suppressed for this section."},"category":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Category","description":"Category override for this section."}},"type":"object","title":"SectionTagOverride","description":"Mirrors `campaign_builder.routers.brand_kit.SectionTagOverride`."},"SectionTagOverridesRequest":{"properties":{"overrides":{"additionalProperties":{"$ref":"#/components/schemas/SectionTagOverride"},"type":"object","title":"Overrides","description":"Section id -> tag override."}},"type":"object","title":"SectionTagOverridesRequest","description":"Mirrors `campaign_builder.routers.brand_kit.SectionTagOverridesRequest`.\n\nDurable and UPSERTED by section id - sections you do not mention keep the\noverrides they already had."},"SecurityRoleAssignRequest":{"properties":{"role_id":{"type":"string","title":"Role Id","description":"Must match the `role_id` in the path."},"team_member_id":{"type":"string","title":"Team Member Id","description":"Team-member id or the person's user id."},"user_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Name","description":"Required when this creates the team member."},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email","description":"Required when this creates the team member."}},"type":"object","required":["role_id","team_member_id"],"title":"SecurityRoleAssignRequest"},"SeedChannelsRequest":{"properties":{"channels":{"anyOf":[{"items":{"type":"string","enum":["x","linkedin","reddit","instagram","youtube"]},"type":"array"},{"type":"null"}],"title":"Channels"}},"type":"object","title":"SeedChannelsRequest","description":"Which channels an auto-seed targets. Defaults to X alone."},"SeedContext":{"properties":{"primary_keyword":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Primary Keyword"},"volume":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Volume"},"cpc":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Cpc"}},"type":"object","title":"SeedContext","description":"Optional richer seed for an approved stub — e.g. the target keyword (+ volume/cpc)\nto seed an SEO page with. All optional; absent → current behavior unchanged."},"SegmentFilterGroup":{"properties":{"op":{"type":"string","enum":["AND","OR","and","or"],"title":"Op","description":"Connector for this group. Case-insensitive."},"children":{"items":{"anyOf":[{"$ref":"#/components/schemas/SegmentFilterSubgroup"},{"$ref":"#/components/schemas/SegmentFilterLeaf"}]},"type":"array","title":"Children","description":"Nested groups and/or leaf conditions."}},"type":"object","required":["op"],"title":"SegmentFilterGroup","description":"An AND/OR group of leaves and nested groups, at most three groups deep.\n\nMirrors `SegmentFilterGroup` in `contacts.domain.value_objects.ag_grid_models`.\n`op` is closed because the app REFUSES an unrecognised connector rather\nthan defaulting to AND - defaulting would silently return a different\nresult set, and on a destructive route that is a different set of records\nacted on.\n\nFIXED DEPTH, NOT RECURSIVE. The app's model is self-referencing; the\npublished one deliberately is not, because a schema that reaches itself\nthrough `$ref` sends the docs renderer into unbounded recursion. Three\ngroup levels (this one, `SegmentFilterSubgroup`, `SegmentFilterInnerGroup`)\ncover every filter the app's own builder produces; the app's larger depth\nand leaf budget still applies and surfaces as a 422."},"SegmentFilterInnerGroup":{"properties":{"op":{"type":"string","enum":["AND","OR","and","or"],"title":"Op","description":"Connector for this group. Case-insensitive."},"children":{"items":{"$ref":"#/components/schemas/SegmentFilterLeaf"},"type":"array","title":"Children","description":"Leaf conditions."}},"type":"object","required":["op"],"title":"SegmentFilterInnerGroup","description":"The third and deepest group level: leaf conditions only."},"SegmentFilterLeaf":{"properties":{"field":{"type":"string","title":"Field","description":"Column to test, e.g. `CONTACT_JOB_TITLE`."},"op":{"type":"string","enum":["eq","neq","lt","lte","gt","gte","contains","icontains","starts_with","ends_with","in","not_in","between","is_null","is_not_null"],"title":"Op","description":"Comparison to apply."},"value":{"anyOf":[{},{"type":"null"}],"title":"Value","description":"Value to compare against."},"valueTo":{"anyOf":[{},{"type":"null"}],"title":"Valueto","description":"Upper bound. Only meaningful with `between`."}},"type":"object","required":["field","op"],"title":"SegmentFilterLeaf","description":"One field-level condition inside an advanced-filter tree.\n\nMirrors `contacts.domain.value_objects.ag_grid_models.SegmentFilterLeaf`.\n`op` is CLOSED here: the app compiles its UI vocabulary down to this\ncanonical set before sending, and an unrecognised operator reaching the\nSQL builder is a 500 rather than a refusal naming the valid operators."},"SegmentFilterSubgroup":{"properties":{"op":{"type":"string","enum":["AND","OR","and","or"],"title":"Op","description":"Connector for this group. Case-insensitive."},"children":{"items":{"anyOf":[{"$ref":"#/components/schemas/SegmentFilterInnerGroup"},{"$ref":"#/components/schemas/SegmentFilterLeaf"}]},"type":"array","title":"Children","description":"Innermost groups and/or leaf conditions."}},"type":"object","required":["op"],"title":"SegmentFilterSubgroup","description":"The second group level: leaves and/or innermost groups."},"SelectCalendarRequest":{"properties":{"credential_id":{"type":"integer","title":"Credential Id"},"integration":{"type":"string","title":"Integration"},"external_id":{"type":"string","title":"External Id"}},"type":"object","required":["credential_id","integration","external_id"],"title":"SelectCalendarRequest"},"SelectedCalendarEntry":{"properties":{"integration":{"type":"string","title":"Integration"},"external_id":{"type":"string","title":"External Id"},"credential_id":{"type":"integer","title":"Credential Id"},"enabled":{"type":"boolean","title":"Enabled","default":true}},"type":"object","required":["integration","external_id","credential_id"],"title":"SelectedCalendarEntry","description":"One calendar to consult when checking for conflicts."},"SelectedCalendarEnvelope":{"properties":{"data":{"$ref":"#/components/schemas/SelectedCalendarResponse"}},"type":"object","required":["data"],"title":"SelectedCalendarEnvelope","description":"Envelope for POST /calendars/selected."},"SelectedCalendarResponse":{"properties":{"id":{"type":"string","title":"Id"},"integration":{"type":"string","title":"Integration"},"external_id":{"type":"string","title":"External Id"},"credential_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Credential Id"}},"type":"object","required":["id","integration","external_id"],"title":"SelectedCalendarResponse"},"SelectedElementPayload":{"properties":{"element_id":{"type":"string","title":"Element Id"},"tag":{"type":"string","title":"Tag"},"text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Text"},"role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Role"},"section_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Section Id"},"outer_html":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Outer Html"},"scope":{"type":"string","title":"Scope","default":"element"}},"type":"object","required":["element_id","tag"],"title":"SelectedElementPayload","description":"What the visual picker selected, as the rewrite pass needs to see it."},"SendControlRequest":{"properties":{"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason"}},"type":"object","title":"SendControlRequest","description":"Why the send was stopped. Recorded on the send row."},"SendDeliveryBreakdownDTO":{"properties":{"pending":{"type":"integer","title":"Pending","default":0},"sent":{"type":"integer","title":"Sent","default":0},"delivered":{"type":"integer","title":"Delivered","default":0},"bounced":{"type":"integer","title":"Bounced","default":0},"failed":{"type":"integer","title":"Failed","default":0},"opened":{"type":"integer","title":"Opened","default":0}},"type":"object","title":"SendDeliveryBreakdownDTO"},"SendEnvelopeRequest":{"properties":{"custom_message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Custom Message","description":"Overrides the envelope's stored message for this send only."}},"type":"object","title":"SendEnvelopeRequest","description":"Send a draft for signature. This EMAILS A REAL PERSON."},"SendRequest":{"properties":{"body":{"type":"string","title":"Body","description":"Message body to send"},"channel":{"$ref":"#/components/schemas/InboxChannel","description":"Channel to send through: email, sms, or linkedin"},"subject":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subject","description":"Email subject (optional, for email channel)"},"to":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"To","description":"Recipient override (email address or phone number). Omit it to reply to the thread's contact: the contact's email (else the last inbound sender) for email, the thread's contact number for SMS. Not used for LinkedIn."},"from_address":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"From Address","description":"Sender (mailbox email, your phone number, or numeric LinkedIn account ID). Omit it to send from the thread's own mailbox / number / LinkedIn account (the thread's `mailbox`, `from_number` or `linkedin_account_id`). You still need permission to send as that sender."}},"type":"object","required":["body","channel"],"title":"SendRequest"},"SendResponse":{"properties":{"message_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Message Id"},"status":{"type":"string","title":"Status","default":"sent"},"channel":{"type":"string","title":"Channel","default":"email"}},"type":"object","title":"SendResponse"},"SendSurveyRequest":{"properties":{"audience_ref":{"type":"string","minLength":1,"title":"Audience Ref"},"channel":{"type":"string","pattern":"^(email|bridge)$","title":"Channel","default":"email"},"sender_email":{"anyOf":[{"type":"string","format":"email"},{"type":"null"}],"title":"Sender Email"},"subject":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Subject"},"sender_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sender Name"},"reply_to":{"anyOf":[{"type":"string","format":"email"},{"type":"null"}],"title":"Reply To"},"scheduled_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Scheduled At"}},"type":"object","required":["audience_ref"],"title":"SendSurveyRequest"},"SendToSequenceRequest":{"properties":{"sequence_id":{"type":"integer","title":"Sequence Id"},"row_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Row Ids","description":"Rows to send. OMIT to send EVERY row in the table."},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"create_new_list":{"type":"boolean","title":"Create New List","default":false},"new_list_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"New List Name"}},"type":"object","required":["sequence_id"],"title":"SendToSequenceRequest","description":"Put workbench rows into a sequence."},"SenderPersonaWriteRequest":{"properties":{"first_name":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"First Name","description":"Given name"},"last_name":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Last Name","description":"Family name"},"email":{"anyOf":[{"type":"string","maxLength":254},{"type":"null"}],"title":"Email","description":"The persona's own address"},"phone":{"anyOf":[{"type":"string","maxLength":50},{"type":"null"}],"title":"Phone","description":"Contact phone"},"title":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Title","description":"Job title shown in signatures"},"organization":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Organization","description":"Organisation name"},"address_line1":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Address Line1","description":"Registrant address, line 1"},"address_line2":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Address Line2","description":"Registrant address, line 2"},"city":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"City","description":"City"},"state":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"State","description":"State or region"},"country":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Country","description":"Country"},"postal_code":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Postal Code","description":"Postal code"},"photo_url":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Photo Url","description":"Photo URL"},"team_member_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Team Member Id","description":"Team member whose identity this persona uses"}},"additionalProperties":false,"type":"object","title":"SenderPersonaWriteRequest","description":"A sender identity: the real person mail is bought and sent under.\n\nMirrors the app's persona fields (`CreateSenderPersonaData` /\n`SenderPersonaPatch`). The app's own validators - name alphabet, email\nnormalisation, photo URL, \"identity or team member\" - run on the app model\nand surface as a 422, so they are delegated rather than copied here.\n\nOn CREATE: give `first_name`, `last_name` and `email`, or a `team_member_id`\nto take the identity from. On UPDATE: send only what changes; an identity\nfield cannot be set to null."},"SendingWeek":{"properties":{"monday":{"anyOf":[{"$ref":"#/components/schemas/SendingWindow"},{"type":"null"}]},"tuesday":{"anyOf":[{"$ref":"#/components/schemas/SendingWindow"},{"type":"null"}]},"wednesday":{"anyOf":[{"$ref":"#/components/schemas/SendingWindow"},{"type":"null"}]},"thursday":{"anyOf":[{"$ref":"#/components/schemas/SendingWindow"},{"type":"null"}]},"friday":{"anyOf":[{"$ref":"#/components/schemas/SendingWindow"},{"type":"null"}]},"saturday":{"anyOf":[{"$ref":"#/components/schemas/SendingWindow"},{"type":"null"}]},"sunday":{"anyOf":[{"$ref":"#/components/schemas/SendingWindow"},{"type":"null"}]}},"type":"object","title":"SendingWeek","description":"The weekly window. A day left out is a day nothing is sent."},"SendingWindow":{"properties":{"start":{"type":"string","pattern":"^([01]?[0-9]|2[0-3]):[0-5][0-9]$","title":"Start","description":"`HH:MM`, 24-hour."},"end":{"type":"string","pattern":"^([01]?[0-9]|2[0-3]):[0-5][0-9]$","title":"End","description":"`HH:MM`, 24-hour."}},"type":"object","required":["start","end"],"title":"SendingWindow","description":"One day's sending window. `start` must be EARLIER than `end`.\n\nOvernight windows are not supported - model them as two days. The app\nrejects an inverted or zero-length window, and so does this."},"SeoAddTrackedDomainRequest":{"properties":{"domain":{"type":"string","maxLength":255,"minLength":3,"title":"Domain"}},"type":"object","required":["domain"],"title":"SeoAddTrackedDomainRequest","description":"Mirrors `AddTrackedDomainRequest`. The app lower-cases the domain, strips\n`www.` and refuses a scheme or a path with a 422."},"SeoAgentFix":{"properties":{"fix_id":{"type":"string","title":"Fix Id"},"domain":{"type":"string","title":"Domain"},"title":{"type":"string","title":"Title"},"severity":{"type":"string","title":"Severity"},"category":{"type":"string","title":"Category"},"target_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Url"},"why":{"type":"string","title":"Why","default":""},"steps":{"items":{"type":"string"},"type":"array","title":"Steps"},"snippets":{"items":{"$ref":"#/components/schemas/SeoAgentSnippet"},"type":"array","title":"Snippets"},"files":{"additionalProperties":{"type":"string"},"type":"object","title":"Files"},"acceptance":{"items":{"type":"string"},"type":"array","title":"Acceptance"},"status":{"type":"string","title":"Status"}},"type":"object","required":["fix_id","domain","title","severity","category","steps","acceptance","status"],"title":"SeoAgentFix","description":"One fix with exact instructions: the page, the steps, the code to add and how success is checked."},"SeoAgentFixPack":{"properties":{"fix":{"$ref":"#/components/schemas/SeoAgentFix"},"files":{"additionalProperties":{"type":"string"},"type":"object","title":"Files"},"agents_md":{"type":"string","title":"Agents Md"},"claude_md":{"type":"string","title":"Claude Md"}},"type":"object","required":["fix","agents_md","claude_md"],"title":"SeoAgentFixPack"},"SeoAgentFixQueue":{"properties":{"domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain"},"count":{"type":"integer","title":"Count"},"fixes":{"items":{"$ref":"#/components/schemas/SeoAgentFix"},"type":"array","title":"Fixes"},"agents_md":{"type":"string","title":"Agents Md"}},"type":"object","required":["count","fixes","agents_md"],"title":"SeoAgentFixQueue"},"SeoAgentHandoff":{"properties":{"domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain"},"fix_count":{"type":"integer","title":"Fix Count"},"files":{"additionalProperties":{"type":"string"},"type":"object","title":"Files"},"setup":{"$ref":"#/components/schemas/SeoAgentSetup"}},"type":"object","required":["fix_count","files","setup"],"title":"SeoAgentHandoff"},"SeoAgentSetup":{"properties":{"mcp_url":{"type":"string","title":"Mcp Url"},"claude_code":{"type":"string","title":"Claude Code"},"cursor":{"$ref":"#/components/schemas/SeoAgentSetupCursor"},"prompt":{"type":"string","title":"Prompt"},"tools":{"items":{"type":"string"},"type":"array","title":"Tools"}},"type":"object","required":["mcp_url","claude_code","cursor","prompt","tools"],"title":"SeoAgentSetup"},"SeoAgentSetupCursor":{"properties":{"file":{"type":"string","title":"File"},"command":{"type":"string","title":"Command"},"json":{"type":"string","title":"Json"}},"type":"object","required":["file","command","json"],"title":"SeoAgentSetupCursor"},"SeoAgentSnippet":{"properties":{"label":{"type":"string","title":"Label"},"language":{"type":"string","title":"Language","default":""},"code":{"type":"string","title":"Code"},"file_hint":{"type":"string","title":"File Hint","default":""}},"type":"object","required":["label","code"],"title":"SeoAgentSnippet"},"SeoAiReadiness":{"properties":{"domain":{"type":"string","title":"Domain"},"checks":{"items":{"$ref":"#/components/schemas/SeoAiReadinessCheck"},"type":"array","title":"Checks"},"bots":{"items":{"$ref":"#/components/schemas/SeoAiReadinessBot"},"type":"array","title":"Bots"},"passed":{"type":"integer","title":"Passed"},"total":{"type":"integer","title":"Total"}},"type":"object","required":["domain","checks","bots","passed","total"],"title":"SeoAiReadiness","description":"Mirrors `AiReadinessResponse`: llms.txt, AI crawlers in robots.txt and\nhomepage JSON-LD, all free checks."},"SeoAiReadinessBot":{"properties":{"bot":{"type":"string","title":"Bot"},"verdict":{"type":"string","title":"Verdict"},"named":{"type":"boolean","title":"Named"}},"type":"object","required":["bot","verdict","named"],"title":"SeoAiReadinessBot","description":"Mirrors `AiReadinessBotDTO`. `verdict` is allowed, partial or blocked."},"SeoAiReadinessCheck":{"properties":{"id":{"type":"string","title":"Id"},"label":{"type":"string","title":"Label"},"status":{"type":"string","title":"Status"},"detail":{"type":"string","title":"Detail"}},"type":"object","required":["id","label","status","detail"],"title":"SeoAiReadinessCheck","description":"Mirrors `AiReadinessCheckDTO`. `status` is pass, warn, fail or unknown."},"SeoApprovalItem":{"properties":{"fix_id":{"type":"string","title":"Fix Id"},"title":{"type":"string","title":"Title"},"category":{"type":"string","title":"Category"},"severity":{"type":"string","title":"Severity"},"target_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Url"},"delivery":{"type":"string","title":"Delivery"},"impact":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Impact"},"confidence":{"type":"string","enum":["measured","estimated","partial"],"title":"Confidence","default":"estimated"}},"type":"object","required":["fix_id","title","category","severity","delivery"],"title":"SeoApprovalItem"},"SeoApprovalQueue":{"properties":{"count":{"type":"integer","title":"Count"},"items":{"items":{"$ref":"#/components/schemas/SeoApprovalItem"},"type":"array","title":"Items"}},"type":"object","required":["count","items"],"title":"SeoApprovalQueue"},"SeoAudit":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"domain":{"type":"string","title":"Domain"},"status":{"type":"string","title":"Status"},"max_pages":{"type":"integer","title":"Max Pages"},"pages_crawled":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Pages Crawled"},"credits_charged":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Credits Charged"},"onpage_score":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Onpage Score"},"summary_checks":{"additionalProperties":true,"type":"object","title":"Summary Checks","default":{}},"failure_reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Failure Reason"},"enable_javascript":{"type":"boolean","title":"Enable Javascript","default":false},"state":{"$ref":"#/components/schemas/SeoAuditState"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"completed_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Completed At"}},"type":"object","required":["id","domain","status","max_pages","state"],"title":"SeoAudit","description":"Mirrors `AuditDTO`."},"SeoAuditIssue":{"properties":{"issue_type":{"type":"string","title":"Issue Type"},"severity":{"type":"string","title":"Severity"},"affected_count":{"type":"integer","title":"Affected Count"},"affected_total":{"type":"integer","title":"Affected Total","default":0},"affected_urls":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Affected Urls","default":[]}},"type":"object","required":["issue_type","severity","affected_count"],"title":"SeoAuditIssue","description":"Mirrors `AuditIssueDTO`."},"SeoAuditIssues":{"properties":{"audit_id":{"type":"string","format":"uuid","title":"Audit Id"},"issues":{"items":{"$ref":"#/components/schemas/SeoAuditIssue"},"type":"array","title":"Issues"}},"type":"object","required":["audit_id","issues"],"title":"SeoAuditIssues","description":"Mirrors `AuditIssuesResponse`."},"SeoAuditState":{"properties":{"category":{"type":"string","enum":["queued","running","complete","timeout","provider_error","credit_issue","start_error","failed"],"title":"Category","description":"Lifecycle state category driving the plain-language status + recovery UX"},"label":{"type":"string","title":"Label","description":"Short status chip label"},"headline":{"type":"string","title":"Headline","description":"One-line human status"},"detail":{"type":"string","title":"Detail","description":"Plain-language explanation of what happened"},"recovery":{"type":"string","title":"Recovery","description":"Plain-language, safe next step (may be empty)"},"can_run_again":{"type":"boolean","title":"Can Run Again","description":"Whether to offer a manual 'Run a new audit' action"},"is_terminal":{"type":"boolean","title":"Is Terminal","description":"No further automatic progress will happen"},"diagnostic":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Diagnostic","description":"Secondary technical detail (raw provider text)"}},"type":"object","required":["category","label","headline","detail","recovery","can_run_again","is_terminal"],"title":"SeoAuditState","description":"Mirrors `AuditStateDTO` - the plain-language, recovery-oriented view of\nwhere an audit is, so a caller can explain the state rather than parse\nraw provider text."},"SeoBacklinksOverview":{"properties":{"authority_score":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Authority Score"},"total_backlinks":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Total Backlinks"},"referring_domains":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Referring Domains"},"dofollow":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Dofollow"},"nofollow":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Nofollow"}},"type":"object","title":"SeoBacklinksOverview","description":"Mirrors `BacklinksOverviewResponse`."},"SeoCheckKeywordsNowRequest":{"properties":{"keyword_ids":{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":100,"minItems":1,"title":"Keyword Ids"}},"type":"object","required":["keyword_ids"],"title":"SeoCheckKeywordsNowRequest","description":"Mirrors `CheckKeywordsNowRequest`."},"SeoCheckKeywordsNowResponse":{"properties":{"accepted":{"type":"integer","title":"Accepted"}},"type":"object","required":["accepted"],"title":"SeoCheckKeywordsNowResponse","description":"Mirrors `CheckKeywordsNowResponse`: keywords queued for a check now.\nThe rows update as each background check lands."},"SeoClaimFixRequest":{"properties":{"agent":{"anyOf":[{"type":"string","maxLength":80},{"type":"null"}],"title":"Agent","description":"A label for this agent, e.g. claude-code."}},"additionalProperties":false,"type":"object","title":"SeoClaimFixRequest"},"SeoClaimFixResponse":{"properties":{"claimed":{"type":"boolean","title":"Claimed"},"claimed_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Claimed By"},"claim_note":{"type":"string","title":"Claim Note"},"fix":{"$ref":"#/components/schemas/SeoAgentFix"}},"type":"object","required":["claimed","claim_note","fix"],"title":"SeoClaimFixResponse"},"SeoCompleteFixRequest":{"properties":{"agent":{"anyOf":[{"type":"string","maxLength":80},{"type":"null"}],"title":"Agent"},"outcome":{"type":"string","enum":["done","failed"],"title":"Outcome","default":"done"},"ref":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Ref","description":"Commit SHA or commit/pull request URL."},"note":{"type":"string","maxLength":2000,"title":"Note","default":""}},"additionalProperties":false,"type":"object","title":"SeoCompleteFixRequest"},"SeoCompleteFixResponse":{"properties":{"fix_id":{"type":"string","title":"Fix Id"},"status":{"type":"string","title":"Status"},"applied_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Applied Ref"},"verification":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Verification"}},"type":"object","required":["fix_id","status"],"title":"SeoCompleteFixResponse"},"SeoDomainChange":{"properties":{"traffic_pct":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Traffic Pct"},"keywords_delta":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Keywords Delta"},"since":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Since"}},"type":"object","title":"SeoDomainChange","description":"Mirrors `DomainChangeDTO`: the current snapshot against the one nearest\n30 days back. `traffic_pct` is null when the baseline traffic was zero."},"SeoDomainOverviewResponse":{"properties":{"overview":{"additionalProperties":true,"type":"object","title":"Overview"},"top_keywords":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Top Keywords"},"top_pages":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Top Pages"},"data_freshness":{"type":"string","title":"Data Freshness","default":"labs-30-90d"}},"type":"object","required":["overview","top_keywords","top_pages"],"title":"SeoDomainOverviewResponse","description":"Mirrors `DomainOverviewResponse`. `data_freshness` labels how old the\nprovider's view of the domain is - research surfaces must say."},"SeoDomainPage":{"properties":{"url":{"type":"string","title":"Url"},"ranking_keywords_count":{"type":"integer","title":"Ranking Keywords Count"},"estimated_traffic":{"type":"number","title":"Estimated Traffic"},"top_keyword":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Top Keyword"},"best_position":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Best Position"},"traffic_change_30d":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Traffic Change 30D"},"audit_issues":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Audit Issues"}},"type":"object","required":["url","ranking_keywords_count","estimated_traffic"],"title":"SeoDomainPage","description":"Mirrors `DomainPageDTO`."},"SeoDomainPages":{"properties":{"rows":{"items":{"$ref":"#/components/schemas/SeoDomainPage"},"type":"array","title":"Rows"},"total":{"type":"integer","title":"Total"},"cap":{"type":"integer","title":"Cap"},"audit_completed_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Audit Completed At"},"refreshed_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Refreshed At"}},"type":"object","required":["rows","total","cap"],"title":"SeoDomainPages","description":"Mirrors `DomainPagesResponse`. `refreshed_at` is null when the pages\nwere never fetched; `total` counts every saved page, `rows` is one page."},"SeoEndOfDay":{"properties":{"win":{"type":"string","title":"Win"},"risk":{"type":"string","title":"Risk"},"ask":{"type":"string","title":"Ask"},"work_channel_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Work Channel Id"}},"type":"object","required":["win","risk","ask"],"title":"SeoEndOfDay"},"SeoKeywordRow":{"properties":{"keyword":{"type":"string","title":"Keyword"},"search_volume":{"type":"integer","title":"Search Volume","default":0},"keyword_difficulty":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Keyword Difficulty"},"cpc":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Cpc"},"cpc_high":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Cpc High"},"competition":{"type":"number","title":"Competition","default":0},"intent":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Intent"},"intents":{"items":{"type":"string"},"type":"array","title":"Intents","default":[]},"search_volume_avg":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Search Volume Avg"},"volume_spike":{"type":"boolean","title":"Volume Spike","default":false},"trend":{"items":{"type":"integer"},"type":"array","title":"Trend","default":[]},"parent_topic":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Parent Topic"},"parent_topic_volume":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Parent Topic Volume"},"serp_features":{"items":{"type":"string"},"type":"array","title":"Serp Features","default":[]},"results_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Results Count"}},"type":"object","required":["keyword"],"title":"SeoKeywordRow","description":"Mirrors `KeywordRow`."},"SeoMover":{"properties":{"kind":{"type":"string","enum":["rank_up","rank_down","gsc_drop","gsc_gain","low_ctr"],"title":"Kind"},"title":{"type":"string","title":"Title"},"detail":{"type":"string","title":"Detail"},"delta":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Delta"},"from_value":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"From Value"},"to_value":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"To Value"},"url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Url"},"confidence":{"type":"string","enum":["measured","estimated","partial"],"title":"Confidence","default":"measured"}},"type":"object","required":["kind","title","detail"],"title":"SeoMover"},"SeoPage360":{"properties":{"queries":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Queries"},"fixes":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Fixes"}},"additionalProperties":true,"type":"object","title":"SeoPage360","description":"One page in full: its Page360 snapshot plus top queries and open fixes. Extra snapshot keys pass through."},"SeoPages360":{"properties":{"rows":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Rows"},"total":{"type":"integer","title":"Total"},"limit":{"type":"integer","title":"Limit"},"offset":{"type":"integer","title":"Offset"},"gsc_connected":{"type":"boolean","title":"Gsc Connected"},"last_sync_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Sync At"}},"type":"object","required":["rows","total","limit","offset","gsc_connected"],"title":"SeoPages360","description":"The Page360 grid: one row per page with Search Console, vitals, visitors and fix counts."},"SeoRankHistory":{"properties":{"keyword_id":{"type":"string","format":"uuid","title":"Keyword Id"},"snapshots":{"items":{"$ref":"#/components/schemas/SeoRankSnapshot"},"type":"array","title":"Snapshots"}},"type":"object","required":["keyword_id","snapshots"],"title":"SeoRankHistory","description":"Mirrors `RankHistoryResponse`."},"SeoRankSnapshot":{"properties":{"snapshot_date":{"type":"string","format":"date","title":"Snapshot Date"},"rank":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Rank"},"serp_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Serp Url"}},"type":"object","required":["snapshot_date"],"title":"SeoRankSnapshot","description":"Mirrors `RankSnapshotDTO`."},"SeoRemoveTrackedKeywordsRequest":{"properties":{"keyword_ids":{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":100,"minItems":1,"title":"Keyword Ids"}},"type":"object","required":["keyword_ids"],"title":"SeoRemoveTrackedKeywordsRequest","description":"Mirrors `RemoveTrackedKeywordsRequest`."},"SeoRemovedDomain":{"properties":{"removed":{"type":"boolean","title":"Removed"}},"type":"object","required":["removed"],"title":"SeoRemovedDomain","description":"The app answers a bare `{\"removed\": true}` when a tracked domain was\ndeleted; this names the shape so the SDK can type it."},"SeoRemovedKeywords":{"properties":{"removed":{"type":"integer","title":"Removed"}},"type":"object","required":["removed"],"title":"SeoRemovedKeywords","description":"How many tracked keywords the remove call deleted. The app answers a\nbare `{\"removed\": n}`; this names the shape so the SDK can type it."},"SeoResearchKeywordsRequest":{"properties":{"seed_keyword":{"type":"string","maxLength":500,"minLength":1,"title":"Seed Keyword"},"mode":{"type":"string","enum":["auto","ideas","related","suggestions"],"title":"Mode","default":"auto"},"limit":{"type":"integer","maximum":150.0,"minimum":1.0,"title":"Limit","default":150},"location_code":{"type":"integer","title":"Location Code","default":2840},"language_code":{"type":"string","maxLength":10,"title":"Language Code","default":"en"}},"type":"object","required":["seed_keyword"],"title":"SeoResearchKeywordsRequest","description":"Mirrors `ResearchKeywordsRequest`.\n\n`limit` is capped at 150 - the same ceiling the app, the agent tool and the\nUI share - so a larger ask is a 422 here rather than a silent truncation."},"SeoResearchKeywordsResponse":{"properties":{"seed":{"anyOf":[{"$ref":"#/components/schemas/SeoKeywordRow"},{"type":"null"}]},"keywords":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Keywords","default":[]}},"type":"object","title":"SeoResearchKeywordsResponse","description":"Mirrors `ResearchKeywordsResponse`.\n\n`keywords` rows are the provider's row shape for the chosen `mode`, passed\nthrough rather than flattened, because the four modes return different\ncolumns and flattening would drop the ones a caller asked for."},"SeoSaveTrackedKeywordsRequest":{"properties":{"domain":{"type":"string","maxLength":255,"minLength":3,"title":"Domain"},"keywords":{"items":{"$ref":"#/components/schemas/SeoTrackKeywordItem"},"type":"array","maxItems":100,"minItems":1,"title":"Keywords"},"cadence":{"type":"string","enum":["daily","weekly","manual"],"title":"Cadence","default":"daily"},"location_code":{"type":"integer","title":"Location Code","default":2840},"language_code":{"type":"string","maxLength":10,"title":"Language Code","default":"en"}},"type":"object","required":["domain","keywords"],"title":"SeoSaveTrackedKeywordsRequest","description":"Mirrors `SaveTrackedKeywordsRequest`.\n\n`domain` is normalised by the app (lower-cased, `www.` stripped) and\nrefused with a 422 if it carries a scheme or a path."},"SeoSetKeywordCadenceRequest":{"properties":{"keyword_ids":{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":100,"minItems":1,"title":"Keyword Ids"},"cadence":{"type":"string","enum":["daily","weekly","manual"],"title":"Cadence"}},"type":"object","required":["keyword_ids","cadence"],"title":"SeoSetKeywordCadenceRequest","description":"Mirrors `SetKeywordCadenceRequest`."},"SeoSetKeywordTagsRequest":{"properties":{"keyword_ids":{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":100,"minItems":1,"title":"Keyword Ids"},"tags":{"items":{"type":"string","maxLength":60},"type":"array","maxItems":10,"title":"Tags","default":[]}},"type":"object","required":["keyword_ids"],"title":"SeoSetKeywordTagsRequest","description":"Mirrors `SetKeywordTagsRequest`. An empty `tags` list clears the tags."},"SeoSetupChecklist":{"properties":{"items":{"items":{"$ref":"#/components/schemas/SeoSetupItem"},"type":"array","title":"Items"},"done_count":{"type":"integer","title":"Done Count"},"total":{"type":"integer","title":"Total"}},"type":"object","required":["items","done_count","total"],"title":"SeoSetupChecklist"},"SeoSetupItem":{"properties":{"key":{"type":"string","enum":["gsc","domain","competitors","prompts","fix_delivery"],"title":"Key"},"label":{"type":"string","title":"Label"},"done":{"type":"boolean","title":"Done"},"hint":{"type":"string","title":"Hint"},"action":{"$ref":"#/components/schemas/SeoTodayAction"}},"type":"object","required":["key","label","done","hint","action"],"title":"SeoSetupItem"},"SeoShareOfVoice":{"properties":{"domain":{"type":"string","title":"Domain"},"keywords_counted":{"type":"integer","title":"Keywords Counted"},"keywords_with_serp":{"type":"integer","title":"Keywords With Serp"},"share":{"type":"number","title":"Share"},"domains":{"items":{"$ref":"#/components/schemas/SeoShareOfVoiceDomain"},"type":"array","title":"Domains"},"confidence":{"type":"string","title":"Confidence"}},"type":"object","required":["domain","keywords_counted","keywords_with_serp","share","domains","confidence"],"title":"SeoShareOfVoice","description":"Mirrors `ShareOfVoiceResponse`: tracked keywords' latest positions\nthrough a click-through curve, the domain against the others in the top 10."},"SeoShareOfVoiceDomain":{"properties":{"domain":{"type":"string","title":"Domain"},"share":{"type":"number","title":"Share"},"keywords_ranking":{"type":"integer","title":"Keywords Ranking"},"is_us":{"type":"boolean","title":"Is Us"}},"type":"object","required":["domain","share","keywords_ranking","is_us"],"title":"SeoShareOfVoiceDomain","description":"Mirrors `ShareOfVoiceDomainDTO`."},"SeoStartAuditRequest":{"properties":{"domain":{"type":"string","maxLength":255,"minLength":3,"title":"Domain"},"max_pages":{"type":"integer","maximum":500.0,"minimum":10.0,"title":"Max Pages","default":500},"allow_subdomains":{"type":"boolean","title":"Allow Subdomains","default":false},"enable_javascript":{"type":"boolean","title":"Enable Javascript","default":false}},"type":"object","required":["domain"],"title":"SeoStartAuditRequest","description":"Mirrors `StartAuditRequest`. `max_pages` is the crawl ceiling and the\nthing the credit reservation is sized from."},"SeoToday":{"properties":{"domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Domain"},"generated_at":{"type":"string","title":"Generated At"},"kpis":{"items":{"$ref":"#/components/schemas/SeoTodayKpi"},"type":"array","title":"Kpis"},"briefing":{"items":{"$ref":"#/components/schemas/SeoTodayCard"},"type":"array","title":"Briefing"},"approval_queue":{"$ref":"#/components/schemas/SeoApprovalQueue"},"movers":{"items":{"$ref":"#/components/schemas/SeoMover"},"type":"array","title":"Movers"},"alerts":{"items":{"$ref":"#/components/schemas/SeoTodayAlert"},"type":"array","title":"Alerts"},"end_of_day":{"$ref":"#/components/schemas/SeoEndOfDay"},"setup":{"$ref":"#/components/schemas/SeoSetupChecklist"},"health_score":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Health Score"},"sources":{"additionalProperties":{"type":"boolean"},"type":"object","title":"Sources"}},"type":"object","required":["generated_at","kpis","briefing","approval_queue","movers","alerts","end_of_day","setup"],"title":"SeoToday","description":"Today in Signals > SEO: KPIs, the briefing, the approval queue, movers, alerts and the setup checklist."},"SeoTodayAction":{"properties":{"label":{"type":"string","title":"Label"},"kind":{"type":"string","enum":["goto_tab","settings","approve_fix","link"],"title":"Kind"},"tab":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Tab"},"href":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Href"},"fix_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Fix Id"}},"type":"object","required":["label","kind"],"title":"SeoTodayAction"},"SeoTodayAlert":{"properties":{"id":{"type":"string","title":"Id"},"kind":{"type":"string","title":"Kind"},"severity":{"type":"string","enum":["critical","high","medium","low"],"title":"Severity"},"title":{"type":"string","title":"Title"},"body":{"type":"string","title":"Body"},"fired_at":{"type":"string","title":"Fired At"},"payload":{"additionalProperties":true,"type":"object","title":"Payload"},"action":{"anyOf":[{"$ref":"#/components/schemas/SeoTodayAction"},{"type":"null"}]}},"type":"object","required":["id","kind","severity","title","body","fired_at"],"title":"SeoTodayAlert"},"SeoTodayCard":{"properties":{"id":{"type":"string","title":"Id"},"category":{"type":"string","title":"Category"},"severity":{"type":"string","enum":["critical","high","medium","low"],"title":"Severity"},"title":{"type":"string","title":"Title"},"detail":{"type":"string","title":"Detail"},"stake":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stake"},"confidence":{"type":"string","enum":["measured","estimated","partial"],"title":"Confidence","default":"measured"},"action":{"$ref":"#/components/schemas/SeoTodayAction"}},"type":"object","required":["id","category","severity","title","detail","action"],"title":"SeoTodayCard"},"SeoTodayKpi":{"properties":{"key":{"type":"string","title":"Key"},"label":{"type":"string","title":"Label"},"value":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Value"},"delta_pct":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Delta Pct"},"confidence":{"type":"string","enum":["measured","estimated","partial"],"title":"Confidence","default":"measured"},"hint":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Hint"}},"type":"object","required":["key","label"],"title":"SeoTodayKpi"},"SeoTrackKeywordItem":{"properties":{"keyword":{"type":"string","maxLength":500,"minLength":1,"title":"Keyword"},"search_volume":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Search Volume"}},"type":"object","required":["keyword"],"title":"SeoTrackKeywordItem","description":"Mirrors `TrackKeywordItem`."},"SeoTrackedDomain":{"properties":{"domain":{"type":"string","title":"Domain"},"kind":{"type":"string","enum":["own","competitor"],"title":"Kind"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"is_primary":{"type":"boolean","title":"Is Primary","default":false},"snapshot_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Snapshot At"},"metrics":{"anyOf":[{"$ref":"#/components/schemas/SeoTrackedDomainMetrics"},{"type":"null"}]},"change_30d":{"anyOf":[{"$ref":"#/components/schemas/SeoDomainChange"},{"type":"null"}]}},"type":"object","required":["domain","kind"],"title":"SeoTrackedDomain","description":"Mirrors `TrackedDomainDTO`. `kind` is `own` for the organisation's own\nsites and `competitor` for the Radar competitors shown beside them."},"SeoTrackedDomainDetail":{"properties":{"domain":{"type":"string","title":"Domain"},"kind":{"type":"string","enum":["own","competitor"],"title":"Kind"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"is_primary":{"type":"boolean","title":"Is Primary","default":false},"snapshot_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Snapshot At"},"metrics":{"anyOf":[{"$ref":"#/components/schemas/SeoTrackedDomainMetrics"},{"type":"null"}]},"change_30d":{"anyOf":[{"$ref":"#/components/schemas/SeoDomainChange"},{"type":"null"}]},"overview":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Overview"},"top_keywords":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Top Keywords","default":[]},"top_pages":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Top Pages","default":[]},"backlinks":{"anyOf":[{"$ref":"#/components/schemas/SeoBacklinksOverview"},{"type":"null"}]},"data_freshness":{"type":"string","title":"Data Freshness","default":"labs-30-90d"},"refreshed":{"type":"boolean","title":"Refreshed","default":false}},"type":"object","required":["domain","kind"],"title":"SeoTrackedDomainDetail","description":"Mirrors `TrackedDomainDetailResponse`: one domain's saved snapshot,\nrendered without any paid call. Empty until the first refresh in the app."},"SeoTrackedDomainMetrics":{"properties":{"organic_keywords":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Organic Keywords"},"estimated_traffic":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Estimated Traffic"},"top3_positions":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Top3 Positions"},"authority_score":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Authority Score"},"referring_domains":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Referring Domains"},"traffic_basis":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Traffic Basis"}},"type":"object","title":"SeoTrackedDomainMetrics","description":"Mirrors `TrackedDomainMetricsDTO`."},"SeoTrackedDomains":{"properties":{"domains":{"items":{"$ref":"#/components/schemas/SeoTrackedDomain"},"type":"array","title":"Domains"},"max_own_domains":{"type":"integer","title":"Max Own Domains"},"refresh_credits":{"type":"integer","title":"Refresh Credits"},"research_credits":{"type":"integer","title":"Research Credits","default":1},"pages_max_credits":{"type":"integer","title":"Pages Max Credits"},"pages_cap":{"type":"integer","title":"Pages Cap"},"page_keywords_credits":{"type":"integer","title":"Page Keywords Credits"},"page_keywords_limit":{"type":"integer","title":"Page Keywords Limit"}},"type":"object","required":["domains","max_own_domains","refresh_credits","pages_max_credits","pages_cap","page_keywords_credits","page_keywords_limit"],"title":"SeoTrackedDomains","description":"Mirrors `TrackedDomainsResponse`: the saved domains (own first, primary\nfirst, then competitors) plus the credit price of each paid refresh, so a\ncaller can quote the cost before anyone asks for one."},"SeoTrackedKeyword":{"properties":{"id":{"type":"string","format":"uuid","title":"Id"},"domain":{"type":"string","title":"Domain"},"keyword":{"type":"string","title":"Keyword"},"cadence":{"type":"string","title":"Cadence"},"location_code":{"type":"integer","title":"Location Code"},"language_code":{"type":"string","title":"Language Code"},"latest_rank":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Latest Rank"},"latest_serp_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Latest Serp Url"},"latest_checked_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Latest Checked At"},"search_volume":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Search Volume"},"latest_serp_depth":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Latest Serp Depth"},"serp_features":{"items":{"type":"string"},"type":"array","title":"Serp Features","default":[]},"tags":{"items":{"type":"string"},"type":"array","title":"Tags","default":[]},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"}},"type":"object","required":["id","domain","keyword","cadence","location_code","language_code"],"title":"SeoTrackedKeyword","description":"Mirrors `TrackedKeywordDTO`."},"SeoUpdatedKeywords":{"properties":{"updated":{"type":"integer","title":"Updated"}},"type":"object","required":["updated"],"title":"SeoUpdatedKeywords","description":"How many tracked keywords a tags or cadence change touched. The app\nanswers a bare `{\"updated\": n}`; this names the shape for the SDK."},"SequenceActionResponse":{"properties":{"sequence_id":{"type":"string","title":"Sequence Id"},"status":{"type":"string","title":"Status"},"contacts_affected":{"type":"integer","title":"Contacts Affected","default":0}},"type":"object","required":["sequence_id","status"],"title":"SequenceActionResponse"},"SequenceAnalyticsResponse":{"properties":{"overview":{"additionalProperties":true,"type":"object","title":"Overview"},"performance":{"additionalProperties":true,"type":"object","title":"Performance"},"engagement":{"additionalProperties":true,"type":"object","title":"Engagement"},"timeline":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Timeline"},"contact_distribution":{"additionalProperties":true,"type":"object","title":"Contact Distribution"},"step_breakdown":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Step Breakdown"},"step_creation_methods":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Step Creation Methods"},"sender_distribution":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Sender Distribution"}},"type":"object","title":"SequenceAnalyticsResponse"},"SequenceCalendarPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"SequenceCalendarPayload","description":"A sequence calendar read or action result (plan, when, who, org calendar, skip, send-now), as the app returns it."},"SequenceCampaignLinkRequest":{"properties":{"campaign_id":{"type":"string","title":"Campaign Id","description":"Studio campaign id to link."}},"type":"object","required":["campaign_id"],"title":"SequenceCampaignLinkRequest","description":"Link a sequence to a Studio campaign."},"SequenceContactItem":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"contact_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Contact Id"},"state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"State"},"current_step_order":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Current Step Order"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"}},"type":"object","title":"SequenceContactItem"},"SequenceCreateRequest":{"properties":{"name":{"type":"string","title":"Name","description":"Sequence name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Sequence description"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email","description":"Owner email address. Omit it to make the person who minted this API key the owner (org keys that record no creator must still send it)."},"finish_on_reply":{"type":"boolean","title":"Finish On Reply","description":"Stop contacting on reply","default":true},"send_in_same_thread":{"type":"boolean","title":"Send In Same Thread","description":"Send follow-ups in same email thread","default":false},"wait_for_new_contacts":{"type":"boolean","title":"Wait For New Contacts","description":"Keep sequence waiting for new contacts","default":false},"associated_list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Associated List Id","description":"Contact list to associate"},"steps":{"anyOf":[{"items":{"$ref":"#/components/schemas/StepConfig"},"type":"array"},{"type":"null"}],"title":"Steps","description":"Sequence steps to create"},"channels":{"anyOf":[{"items":{"$ref":"#/components/schemas/ChannelConfig"},"type":"array"},{"type":"null"}],"title":"Channels","description":"Channels to attach"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id","description":"AI Studio campaign to link"},"sequence_kind":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Kind","description":"Sequence kind: 'cold_outbound' (default) or 'nurture'. Immutable after creation. 'nurture' requires pinned_mailbox_id and is gated by the ENABLE_NURTURE feature flag.","default":"cold_outbound"},"pinned_mailbox_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Pinned Mailbox Id","description":"Mailbox ID to pin for a nurture sequence. Required when sequence_kind='nurture'; all email channels must use this mailbox. Ignored for cold_outbound sequences."}},"type":"object","required":["name"],"title":"SequenceCreateRequest"},"SequenceCreateResponse":{"properties":{"id":{"type":"string","title":"Id"},"name":{"type":"string","title":"Name"},"status":{"type":"string","title":"Status"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"}},"type":"object","required":["id","name","status"],"title":"SequenceCreateResponse"},"SequenceDetailResponse":{"properties":{"id":{"type":"string","title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email"},"associated_list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Associated List Id"},"finish_on_reply":{"type":"boolean","title":"Finish On Reply","default":false},"send_in_same_thread":{"type":"boolean","title":"Send In Same Thread","default":false},"wait_for_new_contacts":{"type":"boolean","title":"Wait For New Contacts","default":false},"schedule_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Schedule Id"},"appointment_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Appointment Id"},"textual_agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Textual Agent Name"},"voice_agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Voice Agent Name"},"paused_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Paused At"},"resumed_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Resumed At"},"sequence_kind":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Kind"},"pinned_mailbox_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Pinned Mailbox Id"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["id"],"title":"SequenceDetailResponse"},"SequenceDuplicateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Name for the copy. Defaults to the source name with ' (Copy)' appended."},"is_shared":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Shared","description":"Share setting for the copy. Omit to INHERIT the source's - which means duplicating an already-shared sequence can still require Admin/Owner even though this field was never sent."},"is_new_list":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is New List","description":"Give the copy a fresh contacts list instead of the source's."},"new_list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"New List Id","description":"Existing list for the copy. Ignored unless `is_new_list` is true."}},"type":"object","title":"SequenceDuplicateRequest","description":"Copy a sequence. The copy is owned by the caller and starts drafted.\n\n`user_email` is deliberately absent: the app pins the copy's owner to the\ncaller, so accepting the field would advertise control it does not grant."},"SequenceInmailPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"SequenceInmailPayload","description":"An InMail preparation job, its per-contact readiness rows, or a cancel result."},"SequenceListItem":{"properties":{"id":{"type":"string","title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email"},"step_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Step Count"},"contact_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Contact Count"},"sequence_kind":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Kind"},"associated_list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Associated List Id"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["id"],"title":"SequenceListItem"},"SequenceMixAndMatchPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"SequenceMixAndMatchPayload","description":"A mix-and-match summary, preview or apply result, as the app returns it."},"SequenceOpsPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"SequenceOpsPayload","description":"A sequence contact, report, step list or job status, as the app returns it."},"SequencePreviewResponse":{"properties":{"id":{"type":"string","title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"steps":{"items":{"$ref":"#/components/schemas/PreviewStepItem"},"type":"array","title":"Steps"},"channels":{"items":{"$ref":"#/components/schemas/PreviewChannelItem"},"type":"array","title":"Channels"}},"type":"object","required":["id"],"title":"SequencePreviewResponse"},"SequenceRecord":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"sequence_kind":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Kind"},"is_shared":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Shared"},"is_archived":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Archived"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email","description":"Owner."},"associated_list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Associated List Id"},"campaign_builder_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Builder Campaign Id","description":"Linked Studio campaign, if any."},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated At"}},"additionalProperties":true,"type":"object","title":"SequenceRecord","description":"One sequence, as the lifecycle endpoints return it."},"SequenceRelatedRecordsPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"SequenceRelatedRecordsPayload","description":"Related-record variables, pins or an enrolment result for a sequence."},"SequenceRoutingSummary":{"properties":{"m365_count":{"type":"integer","title":"M365 Count","default":0},"google_count":{"type":"integer","title":"Google Count","default":0},"other_count":{"type":"integer","title":"Other Count","default":0},"bounce_suppressed_count":{"type":"integer","title":"Bounce Suppressed Count","default":0},"seg_suppressed_count":{"type":"integer","title":"Seg Suppressed Count","default":0},"personal_suppressed_count":{"type":"integer","title":"Personal Suppressed Count","default":0},"scanned_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Scanned Count","description":"How many recipients were actually scanned (capped at 10,000)."}},"additionalProperties":true,"type":"object","title":"SequenceRoutingSummary","description":"Approximate provider-routing and suppression breakdown for the list.\n\nTwo properties a caller must not lose:\n\n  * APPROXIMATE - computed by scanning up to 10,000 recipients, not all of\n    them.\n  * FAIL-OPEN - on any error every count is zero, so an all-zero summary\n    means \"could not compute\" just as much as \"nothing matched\". Do not\n    render it as a confident zero.\n\nEach recipient counts toward exactly ONE bucket, suppression taking\nprecedence over routing (bounce > seg > personal), so the buckets are a\npartition and must not be summed alongside each other as if they overlap."},"SequenceStats":{"properties":{"total_contacts":{"type":"integer","title":"Total Contacts","default":0},"step_stats":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Step Stats"},"skip_reason_breakdown":{"additionalProperties":{"type":"integer"},"type":"object","title":"Skip Reason Breakdown","description":"Distinct terminal-skipped contacts by raw skip-reason token, e.g. `skipped_too_distant`. Sequence-level, counted once per contact."}},"additionalProperties":true,"type":"object","title":"SequenceStats","description":"Per-step delivery and engagement counts for a sequence.\n\n`skip_reason_breakdown` is SEQUENCE-level and counted ONCE per contact, so\nits total can be LESS than the sum of the per-step `skipped` tiles: the\ndurable-LinkedIn-skip cascade writes one receipt per contiguous LinkedIn\nstep, and a skip with no recorded reason is omitted entirely. Presenting\nthe two as if they must reconcile is wrong."},"SequenceStatusRequest":{"properties":{"status":{"type":"string","title":"Status","description":"Target status: drafted, scheduling, live, pausing, paused, resuming, terminating, terminated, completed or waiting. Declared as an open string rather than an enum so a status the sequencer adds is not rejected by a stale copy here - the app's own `SequenceStatus` enum is the source of truth and an unknown value comes back as a 422 that LISTS the valid set."}},"type":"object","required":["status"],"title":"SequenceStatusRequest","description":"Drive the sequence status machine directly.\n\nPrefer the named transitions (`/launch`, `/pause`, `/resume`,\n`/terminate`, `/archive`) - each runs the wind-down, scheduling and event\nwork that belongs to it. This endpoint SETS THE STATUS, and the app's\nstate machine is what rejects an illegal transition."},"SequenceStepRef":{"properties":{"step_id":{"type":"string","title":"Step Id"},"day":{"type":"integer","title":"Day"},"condition":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Condition"},"stop_on_reply":{"type":"boolean","title":"Stop On Reply","default":true}},"type":"object","required":["step_id","day"],"title":"SequenceStepRef"},"SequenceStepsResponse":{"properties":{"sequence_id":{"type":"string","title":"Sequence Id"},"steps":{"items":{"$ref":"#/components/schemas/PreviewStepItem"},"type":"array","title":"Steps"}},"type":"object","required":["sequence_id"],"title":"SequenceStepsResponse","description":"Response for ``GET /sequences/{id}/steps``.\n\nThis route exists because callers reach for it first and used to get a bare\n404, which sent them to ``/preview`` and its unrendered copy instead."},"SequenceTemplateStep":{"properties":{"name":{"type":"string","title":"Name"},"step_type":{"type":"string","enum":["PHONE","EMAIL","MANUAL_DIALER","HEYREACH","NETRION","SMS","WHATSAPP"],"title":"Step Type"},"step_order":{"type":"integer","title":"Step Order"},"input_type":{"type":"string","enum":["ON_DEMAND","AI_GENERATED_TEMPLATE","MANUAL_TEMPLATE"],"title":"Input Type"},"time_interval":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Time Interval","description":"Seconds after the previous step."},"step_data":{"additionalProperties":true,"type":"object","title":"Step Data","description":"The step's content: `subject` / `body` for email, `message_body` for SMS and WhatsApp, the `linkedin_*` fields for LinkedIn, `instructions` for AI generation. The same shape as `step_data` on `GET /sequences/{sequence_id}/steps`."}},"type":"object","required":["name","step_type","step_order","input_type","step_data"],"title":"SequenceTemplateStep","description":"One step of a sequence template. Mirrors `SequenceTemplateStep`."},"SequenceUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Sequence name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Sequence description"},"is_shared":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Shared","description":"Whether sequence is shared"},"finish_on_reply":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Finish On Reply","description":"Finish on reply"},"send_in_same_thread":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Send In Same Thread","description":"Send in same thread"},"wait_for_new_contacts":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Wait For New Contacts","description":"Wait for new contacts"},"schedule_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Schedule Id","description":"Send-window schedule UUID (from GET /schedules). Stamped onto seqsequences.schedule_id."},"appointment_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Appointment Id","description":"Calendar event-type ID (from GET /event-types). Stamped onto seqsequences.appointment_id."},"textual_agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Textual Agent Name","description":"Voice-service agent identifier (from GET /voice/dialer/agents) for email / social steps. Stamped onto seqsequences.textual_agent_name. The same value as voice_agent_name is the common case (one agent across channels)."},"voice_agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Voice Agent Name","description":"Voice-service agent identifier (from GET /voice/dialer/agents) for phone / SMS steps. Stamped onto seqsequences.voice_agent_name."}},"type":"object","title":"SequenceUpdateRequest"},"SequencerListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"SequencerListPayload","description":"An open envelope around a LIST of sequencer records, as `items`."},"SequencerPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"SequencerPayload","description":"An open envelope around one sequencer record.\n\nOpen because templates, schedules and channels carry nested step data and\nconfiguration that grows as channels are added."},"ServiceTokenRequest":{"properties":{"client_id":{"type":"string","title":"Client Id","description":"Service credential client id"},"client_secret":{"type":"string","title":"Client Secret","description":"Service credential client secret (checked against stored hash)"},"scopes":{"items":{"type":"string"},"type":"array","title":"Scopes","description":"Scopes to embed in the token"},"ttl_seconds":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Ttl Seconds","description":"Requested TTL; clamped into the 30-60m service band"}},"type":"object","required":["client_id","client_secret"],"title":"ServiceTokenRequest","description":"Client-credentials exchange for a service (server-to-server) app token."},"SessionCallsLookup":{"properties":{"contact_ids":{"items":{"type":"string"},"type":"array","maxItems":500,"minItems":1,"title":"Contact Ids"}},"type":"object","required":["contact_ids"],"title":"SessionCallsLookup","description":"voice `SessionCallsRequest`."},"SessionDraftRequest":{"properties":{"user_id":{"type":"string","title":"User Id"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email"},"list_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"List Id"},"sequence_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Id"},"sequence_step_order":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Sequence Step Order"},"filter_spec":{"anyOf":[{"$ref":"#/components/schemas/FilterSpec"},{"type":"null"}]},"order_spec":{"anyOf":[{"$ref":"#/components/schemas/OrderSpec"},{"type":"null"}]},"parallel_count":{"type":"integer","title":"Parallel Count","default":1},"from_phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"From Phone"},"agent_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent Id"},"entity_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Type"},"dialing_mode":{"anyOf":[{"type":"string","enum":["power","parallel"]},{"type":"null"}],"title":"Dialing Mode"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id"},"campaign_builder_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Builder Campaign Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"user_timezone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Timezone","default":"America/New_York"},"list_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"List Title"},"selected_event_type_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Selected Event Type Id"}},"type":"object","required":["user_id"],"title":"SessionDraftRequest","description":"Mirrors `CreateBeQueueSessionRequest` minus `org_id`.\n\nEither `list_id` or `sequence_id` is required - voice 400s with neither,\nand that is left to voice rather than duplicated here so the two cannot\ndisagree about which combinations are legal."},"SessionMetadataIn":{"properties":{},"additionalProperties":true,"type":"object","title":"SessionMetadataIn","description":"Free-form session context. Open: voice grows this per release."},"SessionReadRequest":{"properties":{"message_count":{"type":"integer","minimum":0.0,"title":"Message Count","description":"How many messages the caller has actually seen. NOT a flag: the server refuses a count higher than the session holds with a 409, because a client claiming to have read messages that do not exist yet is a stale client, and silently accepting it would mark a later real message read before anyone saw it."}},"type":"object","required":["message_count"],"title":"SessionReadRequest","description":"Mirror of `SessionReadRequest`."},"SessionTokenRequest":{"properties":{"provider":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Provider","description":"Stable graph8 provider name."},"provider_config_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Provider Config Key","description":"Provider config key on the connection provider."}},"type":"object","title":"SessionTokenRequest","description":"Mint a short-lived token for the hosted OAuth flow.\n\nBoth fields are optional because the app's model has them optional - it\nfalls back to its own default provider. They are NOT interchangeable\nspellings of one thing: `provider` is the stable graph8 name and\n`provider_config_key` is the key in the connection provider's own config,\nand the two can differ per environment."},"SetAppLimitRequest":{"properties":{"credit_cap":{"type":"integer","minimum":0.0,"title":"Credit Cap","description":"Hard cap in credits for the window. `0` means 'cap at zero', NOT 'uncapped' -- to remove a cap, DELETE the limit instead."},"window":{"type":"string","title":"Window","description":"Cap window. `calendar_month` is the only value today.","default":"calendar_month"}},"type":"object","required":["credit_cap"],"title":"SetAppLimitRequest","description":"Set an app's hard credit cap for a window.\n\n``window`` is optional and defaults to the only value the enum has today\n(`calendar_month`, D5: fixed monthly allowance, monthly reset, no rollover).\nAccepting it explicitly now means adding a second window later does not\nchange this DTO's shape."},"SetAppStatusRequest":{"properties":{"status":{"type":"string","title":"Status","description":"`draft`, `published`, `suspended` or `archived`. `active` is accepted as the legacy spelling of `published`."}},"type":"object","required":["status"],"title":"SetAppStatusRequest","description":"Mirrors the portal's `setAppStatus(builderOrgId, appId, status)`."},"SetButtonActionRequest":{"properties":{"g8_action_id":{"type":"string","maxLength":120,"minLength":1,"title":"G8 Action Id"},"action_type":{"type":"string","enum":["url","mailto"],"title":"Action Type"},"href":{"anyOf":[{"type":"string","maxLength":2048},{"type":"null"}],"title":"Href","description":"For `url`."},"email":{"anyOf":[{"type":"string","maxLength":320},{"type":"null"}],"title":"Email","description":"For `mailto`."},"target":{"anyOf":[{"type":"string","enum":["_self","_blank"]},{"type":"null"}],"title":"Target"}},"type":"object","required":["g8_action_id","action_type"],"title":"SetButtonActionRequest","description":"Repoint a button.\n\n`action_type` is CLOSED to `url` and `mailto`. The app narrows the wider\nlanding-page action union to those two for email, so a third value reaches\na real `Literal` inside the handler and would escape as a 500."},"SetConfigRequest":{"properties":{"id":{"type":"string","title":"Id","description":"Caller-chosen id."},"name":{"type":"string","title":"Name"},"leaderboard_ids":{"items":{"type":"string"},"type":"array","title":"Leaderboard Ids","description":"The boards to rotate through, in order."},"rotation_seconds":{"type":"integer","title":"Rotation Seconds","description":"Seconds per board. The app's default is 30.","default":30},"is_default":{"type":"boolean","title":"Is Default","default":false},"audio_enabled":{"type":"boolean","title":"Audio Enabled","description":"Whether the display plays a sound on a change.","default":false}},"type":"object","required":["id","name","leaderboard_ids"],"title":"SetConfigRequest","description":"A ROTATION of leaderboards - what a wall display cycles through."},"SetDealColumnValuesRequest":{"properties":{"values":{"additionalProperties":{"anyOf":[{"type":"string"},{"type":"integer"},{"type":"number"},{"type":"boolean"},{"type":"null"}]},"type":"object","title":"Values","description":"Column key -> value. A null clears that column."}},"type":"object","required":["values"],"title":"SetDealColumnValuesRequest","description":"Write custom column values on one deal.\n\n`null` CLEARS a value rather than leaving it alone - this is a write of\nexactly what you send, not a patch that skips nulls."},"SetDefaultConferencingRequest":{"properties":{"credential_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Credential Id"},"link":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Link"}},"type":"object","title":"SetDefaultConferencingRequest"},"SetDestinationCalendarRequest":{"properties":{"integration":{"type":"string","title":"Integration"},"external_id":{"type":"string","title":"External Id"},"credential_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Credential Id"},"event_type_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Event Type Id"}},"type":"object","required":["integration","external_id"],"title":"SetDestinationCalendarRequest"},"SetFieldValueRequest":{"properties":{"record_id":{"type":"integer","title":"Record Id","description":"Contact ID (entity='contacts') or company ID (entity='companies')"},"value":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Value","description":"Value to write into the custom column. Pass null (or omit) to clear the field."},"entity":{"type":"string","title":"Entity","description":"Target entity: 'contacts' or 'companies'","default":"contacts"}},"type":"object","required":["record_id"],"title":"SetFieldValueRequest","description":"Request body for writing a custom column value to a single contact or company row."},"SetFieldValueResponse":{"properties":{"column_id":{"type":"integer","title":"Column Id"},"record_id":{"type":"integer","title":"Record Id"},"updated":{"type":"boolean","title":"Updated","default":true}},"type":"object","required":["column_id","record_id"],"title":"SetFieldValueResponse"},"SetFieldValuesBatchRequest":{"properties":{"rows":{"items":{"$ref":"#/components/schemas/RowFieldValues"},"type":"array","title":"Rows","description":"Rows to update (1-500). Each carries its own record_id + fields[]."},"entity":{"type":"string","title":"Entity","description":"Target entity, SHARED across every row: 'contacts' or 'companies'.","default":"contacts"},"strict":{"type":"boolean","title":"Strict","description":"Opt-in status-code semantics. Default false keeps the historical behaviour: always HTTP 200, per-row outcomes in `results[]`. When true, a batch where EVERY row failed returns 422 and a partially-failed batch returns 207 Multi-Status, so a client that only checks the status code cannot mistake a total failure for success. The response body is identical either way.","default":false}},"type":"object","required":["rows"],"title":"SetFieldValuesBatchRequest","description":"Write custom column values to one OR many contact/company rows at once."},"SetFieldValuesBatchResponse":{"properties":{"entity":{"type":"string","title":"Entity"},"total_rows_requested":{"type":"integer","title":"Total Rows Requested"},"total_rows_updated":{"type":"integer","title":"Total Rows Updated"},"total_values_written":{"type":"integer","title":"Total Values Written"},"results":{"items":{"$ref":"#/components/schemas/SetFieldValuesRowResult"},"type":"array","title":"Results"},"total_rows_failed":{"type":"integer","title":"Total Rows Failed","description":"Rows that could not be written (see results[].error).","default":0},"all_failed":{"type":"boolean","title":"All Failed","description":"True when rows were requested and NONE were written.","default":false}},"type":"object","required":["entity","total_rows_requested","total_rows_updated","total_values_written","results"],"title":"SetFieldValuesBatchResponse"},"SetFieldValuesRowResult":{"properties":{"record_id":{"type":"integer","title":"Record Id"},"ok":{"type":"boolean","title":"Ok","default":true},"updated_columns":{"items":{"type":"integer"},"type":"array","title":"Updated Columns"},"error":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Error","description":"Set when this row failed (record not found, unknown column, etc.). Other rows still commit."}},"type":"object","required":["record_id"],"title":"SetFieldValuesRowResult","description":"Per-row outcome inside a batch value-write response."},"SetImageFocusRequest":{"properties":{"focus_x":{"type":"number","title":"Focus X","default":0.5},"focus_y":{"type":"number","title":"Focus Y","default":0.5}},"type":"object","title":"SetImageFocusRequest","description":"Move the crop focal point, 0-1 in each axis. Spends nothing."},"SetImageRequest":{"properties":{"library_image_id":{"type":"string","title":"Library Image Id"}},"type":"object","required":["library_image_id"],"title":"SetImageRequest","description":"Point the creative at an image already in the library. Spends nothing."},"SetLockedFieldsRequest":{"properties":{"locked_fields":{"items":{"type":"string","enum":["after_event_buffer","before_event_buffer","booking_fields","description","disable_cancelling","disable_guests","disable_rescheduling","event_name","length","locations","minimum_booking_notice","requires_confirmation","slot_interval","title"]},"type":"array","title":"Locked Fields","description":"Fields locked on the managed template. An empty list unlocks everything."}},"type":"object","title":"SetLockedFieldsRequest","description":"Which fields a managed template owns on behalf of every child copy.\n\nClosed to the app's own vocabulary: the app rejects anything else inside\nthe handler, so a free string would fail there instead of as a 422 here\nthat names the valid fields."},"SetMediaEditRequest":{"properties":{"g8_action_id":{"type":"string","maxLength":120,"minLength":1,"title":"G8 Action Id"},"remove":{"type":"boolean","title":"Remove","description":"Delete the image. Other fields are then ignored.","default":false},"src":{"anyOf":[{"type":"string","maxLength":2048},{"type":"null"}],"title":"Src"},"alt":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Alt"},"width":{"anyOf":[{"type":"integer","maximum":3000.0,"minimum":1.0},{"type":"null"}],"title":"Width"},"height":{"anyOf":[{"type":"integer","maximum":3000.0,"minimum":1.0},{"type":"null"}],"title":"Height"},"align":{"anyOf":[{"type":"string","enum":["left","center","right"]},{"type":"null"}],"title":"Align"}},"type":"object","required":["g8_action_id"],"title":"SetMediaEditRequest","description":"Change or remove an image.\n\nEmail surfaces handle `<img>` only - no video and no per-breakpoint\npositioning - which is why this carries a smaller set of fields than the\nlanding-page equivalent."},"SetPipelineEnabledRequest":{"properties":{"enabled":{"type":"boolean","title":"Enabled"}},"type":"object","required":["enabled"],"title":"SetPipelineEnabledRequest","description":"Turn a pipeline on or off.\n\nExplicit rather than a toggle, so a retried request cannot silently restart\na pipeline a caller had just stopped."},"SetTemplateApprovalRequest":{"properties":{"status":{"type":"string","enum":["draft","approved","archived"],"title":"Status"}},"type":"object","required":["status"],"title":"SetTemplateApprovalRequest","description":"Move a template through its lifecycle.\n\n`approved` is what makes it visible in the gallery; `archived` takes it out\nwithout deleting it. Closed to the app's three values."},"SetTextRequest":{"properties":{"element_id":{"type":"string","maxLength":200,"title":"Element Id","description":"`g8` element id from the rendered HTML."},"new_text":{"type":"string","maxLength":5000,"title":"New Text"}},"type":"object","required":["element_id","new_text"],"title":"SetTextRequest","description":"Replace the text of ONE element, exactly as given."},"SettingsCreateRequest":{"properties":{"chat_bot_id":{"type":"string","title":"Chat Bot Id","description":"Owning chat bot id (UUID)."},"surface":{"anyOf":[{"type":"string","enum":["external","internal"]},{"type":"null"}],"title":"Surface","description":"Which widget this theme applies to. Omitted means `external`. `internal` is graph8's own support widget and is refused for any other org."},"primaryColor":{"type":"string","maxLength":20,"title":"Primarycolor","default":"#7E2DF3"},"secondaryColor":{"type":"string","maxLength":20,"title":"Secondarycolor","default":"#f8fafc"},"fontFamily":{"type":"string","maxLength":100,"title":"Fontfamily","default":"Inter"},"fontSize":{"type":"string","maxLength":20,"title":"Fontsize","default":"14px"},"borderRadius":{"type":"string","maxLength":20,"title":"Borderradius","default":"0.5rem"},"chatWidth":{"type":"string","maxLength":20,"title":"Chatwidth","default":"350px"},"darkMode":{"type":"boolean","title":"Darkmode","default":false},"userMessageBgColor":{"type":"string","maxLength":20,"title":"Usermessagebgcolor","default":"#d7d5d5"},"userMessageTextColor":{"type":"string","maxLength":20,"title":"Usermessagetextcolor","default":"#000000"},"assistantMessageBgColor":{"type":"string","maxLength":20,"title":"Assistantmessagebgcolor","default":"#fcfcfc"},"assistantMessageTextColor":{"type":"string","maxLength":20,"title":"Assistantmessagetextcolor","default":"#000000"},"assistantName":{"type":"string","maxLength":100,"title":"Assistantname","default":"Assistant"},"showHeader":{"type":"boolean","title":"Showheader","default":true},"headerTextColor":{"type":"string","maxLength":20,"title":"Headertextcolor","default":"#000000"},"showSuggestedQuestions":{"type":"boolean","title":"Showsuggestedquestions","default":true},"showQuickActions":{"type":"boolean","title":"Showquickactions","default":true},"suggestedQuestionsBgColor":{"type":"string","maxLength":20,"title":"Suggestedquestionsbgcolor","default":"#f0f9ff"},"suggestedQuestionsSectionBgColor":{"type":"string","maxLength":20,"title":"Suggestedquestionssectionbgcolor","default":"#f8fafc"},"robotIconColor":{"type":"string","maxLength":20,"title":"Roboticoncolor","default":"#ffffff"},"robotIconType":{"type":"string","maxLength":50,"title":"Roboticontype","default":"message"},"botIconType":{"type":"string","maxLength":50,"title":"Boticontype","default":"bot"},"headerImageUrlExternal":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Headerimageurlexternal"},"headerImageUrlInternal":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Headerimageurlinternal"},"botAvatarMode":{"type":"string","enum":["agent","preset","custom"],"title":"Botavatarmode","default":"agent"},"botAvatarPresetUrl":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Botavatarpreseturl"},"botAvatarCustomUrl":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Botavatarcustomurl"},"themeSource":{"type":"string","enum":["default","brand_kit","custom"],"title":"Themesource","default":"default"},"designTokens":{"anyOf":[{"$ref":"#/components/schemas/DesignTokens"},{"type":"null"}],"description":"Design-token tree. The app's own model, so the magnitude guard runs here rather than inside the proxy."},"copyOverrides":{"anyOf":[{"additionalProperties":{"type":"string"},"type":"object"},{"type":"null"}],"title":"Copyoverrides"}},"type":"object","required":["chat_bot_id"],"title":"SettingsCreateRequest","description":"The widget's whole appearance and behaviour, for one bot and surface.\n\nEvery colour is validated as a hex value, every dimension as a CSS length,\nand two MODEL-level guards reject an illegible text/background pair and an\nabsurd design-token magnitude. All of those live in the app's model, which\nis what this mirrors - see the module docstring on why `designTokens` is\nimported rather than re-declared.\n\nONE SETTINGS ROW PER (bot, surface). Creating a second is a 409, not a\nsecond row; use `PATCH /webchat/settings` to change one that exists."},"SettingsListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"SettingsListPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape."},"SettingsPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"SettingsPayload","description":"An open envelope for a settings object.\n\nOpen because an ontology concept and an SSO config both grow fields as the\nproduct does, and on a settings read a dropped field reads as \"not\nconfigured\" rather than \"we did not tell you\"."},"SettingsUpdateRequest":{"properties":{"chat_bot_id":{"type":"string","title":"Chat Bot Id","description":"Owning chat bot id (UUID)."},"expected_revision":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Expected Revision"},"surface":{"anyOf":[{"type":"string","enum":["external","internal"]},{"type":"null"}],"title":"Surface"},"primaryColor":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Primarycolor"},"secondaryColor":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Secondarycolor"},"fontFamily":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Fontfamily"},"fontSize":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Fontsize"},"borderRadius":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Borderradius"},"chatWidth":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Chatwidth"},"darkMode":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Darkmode"},"userMessageBgColor":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Usermessagebgcolor"},"userMessageTextColor":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Usermessagetextcolor"},"assistantMessageBgColor":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Assistantmessagebgcolor"},"assistantMessageTextColor":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Assistantmessagetextcolor"},"assistantName":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Assistantname"},"showHeader":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Showheader"},"headerTextColor":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Headertextcolor"},"showSuggestedQuestions":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Showsuggestedquestions"},"showQuickActions":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Showquickactions"},"suggestedQuestionsBgColor":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Suggestedquestionsbgcolor"},"suggestedQuestionsSectionBgColor":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Suggestedquestionssectionbgcolor"},"robotIconColor":{"anyOf":[{"type":"string","maxLength":20},{"type":"null"}],"title":"Roboticoncolor"},"robotIconType":{"anyOf":[{"type":"string","maxLength":50},{"type":"null"}],"title":"Roboticontype"},"botIconType":{"anyOf":[{"type":"string","maxLength":50},{"type":"null"}],"title":"Boticontype"},"headerImageUrlExternal":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Headerimageurlexternal"},"headerImageUrlInternal":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Headerimageurlinternal"},"botAvatarMode":{"anyOf":[{"type":"string","enum":["agent","preset","custom"]},{"type":"null"}],"title":"Botavatarmode"},"botAvatarPresetUrl":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Botavatarpreseturl"},"botAvatarCustomUrl":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Botavatarcustomurl"},"themeSource":{"anyOf":[{"type":"string","enum":["default","brand_kit","custom"]},{"type":"null"}],"title":"Themesource"},"designTokens":{"anyOf":[{"$ref":"#/components/schemas/DesignTokens"},{"type":"null"}]},"themeOverridesRemove":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":64},{"type":"null"}],"title":"Themeoverridesremove","description":"Token paths to REMOVE. Unsetting a token is not the same as this."},"copyOverrides":{"anyOf":[{"additionalProperties":{"type":"string"},"type":"object"},{"type":"null"}],"title":"Copyoverrides"},"launcherQuestionLimit":{"anyOf":[{"type":"integer","maximum":20.0,"minimum":0.0},{"type":"null"}],"title":"Launcherquestionlimit"},"homeQuestionLimit":{"anyOf":[{"type":"integer","maximum":20.0,"minimum":0.0},{"type":"null"}],"title":"Homequestionlimit"},"conversationQuestionLimit":{"anyOf":[{"type":"integer","maximum":20.0,"minimum":0.0},{"type":"null"}],"title":"Conversationquestionlimit"},"conversationQuestionsAfterFirstMessage":{"anyOf":[{"type":"string","enum":["hide","remain","collapse"]},{"type":"null"}],"title":"Conversationquestionsafterfirstmessage"}},"type":"object","required":["chat_bot_id"],"title":"SettingsUpdateRequest","description":"Partial edit of the widget theme. An unset field is left untouched.\n\n`themeOverridesRemove` is the only way to DELETE a token override rather\nthan set it to something - sending `null` for a token would be \"unset in\nthis request\", which the partial-update rule reads as \"leave it alone\"."},"SetupWarmupRequest":{"properties":{"mailbox_id":{"type":"integer","title":"Mailbox Id"},"provider":{"type":"string","title":"Provider","description":"The warmup provider to enrol with."},"warmup_settings":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Warmup Settings","description":"Provider-specific settings. Open because the accepted keys differ per provider and change with them - the app passes this through untouched, and a closed mirror here would drop a setting the provider supports."}},"type":"object","required":["mailbox_id","provider"],"title":"SetupWarmupRequest","description":"Put a mailbox onto a warmup provider."},"ShortlistExportRequest":{"properties":{"name":{"type":"string","maxLength":200,"minLength":1,"title":"Name","description":"The new list's title."},"sdr_profile_ids":{"items":{"type":"string"},"type":"array","maxItems":200,"minItems":1,"title":"Sdr Profile Ids","description":"Talent profile ids (UUID). Anonymous talent you have not hired are skipped."}},"type":"object","required":["name","sdr_profile_ids"],"title":"ShortlistExportRequest","description":"Turn a shortlist of talent into a contacts list in your workspace."},"SignatureArchiveResponse":{"properties":{"archived":{"type":"boolean","title":"Archived"}},"type":"object","required":["archived"],"title":"SignatureArchiveResponse"},"SignatureAssignment":{"properties":{"member_id":{"type":"string","format":"uuid","title":"Member Id"},"template_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Template Id"},"account_subject":{"type":"string","maxLength":255,"minLength":3,"title":"Account Subject"},"send_as_email":{"type":"string","maxLength":255,"minLength":3,"title":"Send As Email"},"integration_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Integration Id"},"overrides":{"additionalProperties":{"type":"string"},"type":"object","title":"Overrides"},"native_requested":{"type":"boolean","title":"Native Requested","default":false}},"additionalProperties":false,"type":"object","required":["member_id","account_subject","send_as_email"],"title":"SignatureAssignment","description":"Which employee a mailbox signs as, and which template it renders."},"SignatureAssignmentResult":{"properties":{"mailbox_id":{"type":"integer","title":"Mailbox Id"},"revision":{"type":"integer","title":"Revision"}},"type":"object","required":["mailbox_id","revision"],"title":"SignatureAssignmentResult"},"SignatureAssignmentWrite":{"properties":{"expected_revisions":{"additionalProperties":{"type":"integer"},"type":"object","title":"Expected Revisions","description":"mailbox_id -> revision you last read. Use 0 for a mailbox with no assignment yet."},"confirm_takeover":{"type":"boolean","const":true,"title":"Confirm Takeover","description":"Must be true. Acknowledges that the mailbox's current signature is replaced."},"mailbox_ids":{"items":{"type":"integer"},"type":"array","maxItems":1000,"minItems":1,"title":"Mailbox Ids"},"data":{"$ref":"#/components/schemas/SignatureAssignment"}},"type":"object","required":["expected_revisions","confirm_takeover","mailbox_ids","data"],"title":"SignatureAssignmentWrite","description":"Bind an employee identity to one or more mailboxes.\n\n``confirm_takeover`` must be ``true``: assignment replaces whatever signature\nthose mailboxes send today, and the original is captured for restore."},"SignatureBulkPushRequest":{"properties":{"mailbox_ids":{"items":{"type":"integer"},"type":"array","maxItems":1000,"minItems":1,"title":"Mailbox Ids"}},"type":"object","required":["mailbox_ids"],"title":"SignatureBulkPushRequest"},"SignatureBulkTemplateResponse":{"properties":{"count":{"type":"integer","title":"Count"},"results":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Results"}},"type":"object","required":["count","results"],"title":"SignatureBulkTemplateResponse"},"SignatureCampaign":{"properties":{"name":{"type":"string","maxLength":150,"minLength":1,"title":"Name"},"block":{"$ref":"#/components/schemas/Block"},"starts_at":{"type":"string","format":"date-time","title":"Starts At"},"ends_at":{"type":"string","format":"date-time","title":"Ends At"},"status":{"type":"string","enum":["draft","scheduled","paused"],"title":"Status","default":"draft"},"priority":{"type":"integer","maximum":1000.0,"minimum":-1000.0,"title":"Priority","default":0},"mailbox_ids":{"items":{"type":"integer"},"type":"array","maxItems":10000,"title":"Mailbox Ids"},"recipient_domains":{"items":{"type":"string"},"type":"array","maxItems":1000,"title":"Recipient Domains"},"excluded_domains":{"items":{"type":"string"},"type":"array","maxItems":1000,"title":"Excluded Domains"},"external_only":{"type":"boolean","title":"External Only","default":true},"departments":{"items":{"type":"string"},"type":"array","maxItems":1000,"title":"Departments"},"recipient_list_ids":{"items":{"type":"integer"},"type":"array","maxItems":1000,"title":"Recipient List Ids"},"native_static":{"type":"boolean","title":"Native Static","default":false}},"additionalProperties":false,"type":"object","required":["name","block","starts_at","ends_at"],"title":"SignatureCampaign","description":"A time-boxed banner campaign injected into managed signatures."},"SignatureCampaignPreviewRequest":{"properties":{"version":{"type":"integer","title":"Version","description":"Revision you last read. Ignored on create.","default":0},"data":{"$ref":"#/components/schemas/SignatureCampaign"},"mailbox_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Mailbox Id","description":"Evaluate the campaign's targeting rules against this mailbox. Omit to render only."},"recipients":{"items":{"type":"string"},"type":"array","maxItems":100,"title":"Recipients","description":"Candidate recipient addresses to test the targeting rules against."},"campaign_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Campaign Id","description":"Exclude this campaign from the priority comparison when previewing an edit."}},"type":"object","required":["data"],"title":"SignatureCampaignPreviewRequest","description":"Render a campaign banner without saving it, optionally against a mailbox."},"SignatureCampaignPreviewResponse":{"properties":{"html":{"type":"string","title":"Html"},"plain":{"type":"string","title":"Plain"},"native_static":{"type":"boolean","title":"Native Static"},"matching":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Matching","description":"Targeting evaluation. Null unless mailbox_id was supplied."}},"type":"object","required":["html","plain","native_static"],"title":"SignatureCampaignPreviewResponse"},"SignatureCampaignResponse":{"properties":{"id":{"type":"string","title":"Id"},"revision":{"type":"integer","title":"Revision"},"data":{"additionalProperties":true,"type":"object","title":"Data","description":"The stored campaign document."}},"type":"object","required":["id","revision","data"],"title":"SignatureCampaignResponse"},"SignatureCampaignWrite":{"properties":{"version":{"type":"integer","title":"Version","description":"Revision you last read. Ignored on create.","default":0},"data":{"$ref":"#/components/schemas/SignatureCampaign"}},"type":"object","required":["data"],"title":"SignatureCampaignWrite","description":"Create or update a signature banner campaign."},"SignatureDeploymentStatus":{"properties":{"revision":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Revision"},"status":{"type":"string","title":"Status"},"message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Message"}},"type":"object","required":["status"],"title":"SignatureDeploymentStatus","description":"The outcome of a deployment-changing operation."},"SignatureMember":{"properties":{"id":{"type":"string","title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"},"department":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Department"}},"type":"object","required":["id"],"title":"SignatureMember","description":"A directory employee who can be assigned a managed signature."},"SignaturePreviewRequest":{"properties":{"data":{"$ref":"#/components/schemas/SignatureTemplate"},"mailbox_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Mailbox Id"},"member_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Member Id","description":"Render with this employee's real details. Requires mailbox_id; otherwise sample data is used."},"overrides":{"additionalProperties":{"type":"string"},"type":"object","title":"Overrides"}},"type":"object","required":["data"],"title":"SignaturePreviewRequest","description":"Render an unsaved template draft."},"SignatureRevision":{"properties":{"version":{"type":"integer","title":"Version","description":"Revision you last read. A mismatch is a 409."}},"type":"object","required":["version"],"title":"SignatureRevision","description":"Optimistic-concurrency token for a per-mailbox deployment or a template."},"SignatureSavedPreviewRequest":{"properties":{"mailbox_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Mailbox Id"},"member_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Member Id"}},"type":"object","title":"SignatureSavedPreviewRequest","description":"Render a template that is already stored."},"SignatureSettings":{"properties":{"mode":{"type":"string","enum":["off","default","enforced"],"title":"Mode","default":"off"},"default_template_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Default Template Id"},"department_templates":{"additionalProperties":{"type":"string","format":"uuid"},"type":"object","title":"Department Templates"},"allow_employee_overrides":{"type":"boolean","title":"Allow Employee Overrides","default":true},"cold_sends_variant":{"type":"string","enum":["full","compact"],"title":"Cold Sends Variant","default":"compact"},"native_enabled":{"type":"boolean","title":"Native Enabled","default":false}},"additionalProperties":false,"type":"object","title":"SignatureSettings","description":"Org-wide signature policy document. Same contract as the in-app editor."},"SignatureSettingsResponse":{"properties":{"version":{"type":"integer","title":"Version","description":"Version after the write; pass it to the next update."},"data":{"additionalProperties":true,"type":"object","title":"Data","description":"The stored policy document."}},"type":"object","required":["version","data"],"title":"SignatureSettingsResponse"},"SignatureSettingsWrite":{"properties":{"version":{"type":"integer","title":"Version","description":"Version you last read. A mismatch is a 409."},"data":{"$ref":"#/components/schemas/SignatureSettings"}},"type":"object","required":["version","data"],"title":"SignatureSettingsWrite","description":"Replace the org-wide signature policy. Optimistic-concurrency checked."},"SignatureSetupPreviewRequest":{"properties":{"mailbox_id":{"type":"integer","title":"Mailbox Id"},"data":{"$ref":"#/components/schemas/SignatureAssignment"}},"type":"object","required":["mailbox_id","data"],"title":"SignatureSetupPreviewRequest","description":"Check that a mailbox's provider account and send-as alias are usable."},"SignatureSourceWrite":{"properties":{"version":{"type":"integer","title":"Version","description":"Revision you last read. A mismatch is a 409."},"source":{"type":"string","enum":["org","template","custom"],"title":"Source"},"template_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Template Id","description":"Required when source is 'template'."}},"type":"object","required":["version","source"],"title":"SignatureSourceWrite","description":"Switch which signature a mailbox sends: org default, a named template, or its own."},"SignatureTemplate":{"properties":{"name":{"type":"string","maxLength":150,"minLength":1,"title":"Name"},"layout":{"type":"string","enum":["classic-stacked","photo-left","logo-left","two-column","compact-inline","banner-hero"],"title":"Layout","default":"classic-stacked"},"blocks":{"items":{"$ref":"#/components/schemas/Block"},"type":"array","maxItems":30,"minItems":1,"title":"Blocks"},"primary_color":{"type":"string","pattern":"^#[a-fA-F0-9]{6}$","title":"Primary Color","default":"#222222"},"font":{"type":"string","enum":["Arial","Verdana","Georgia","Tahoma"],"title":"Font","default":"Arial"},"brand_source":{"type":"string","enum":["brand_kit","custom"],"title":"Brand Source","default":"brand_kit"}},"additionalProperties":false,"type":"object","required":["name","blocks"],"title":"SignatureTemplate","description":"A signature template's blocks, layout and branding."},"SignatureTemplateResponse":{"properties":{"id":{"type":"string","title":"Id"},"version":{"type":"integer","title":"Version"},"data":{"additionalProperties":true,"type":"object","title":"Data","description":"The stored template document."}},"type":"object","required":["id","version","data"],"title":"SignatureTemplateResponse"},"SignatureTemplateTargets":{"properties":{"mailbox_ids":{"items":{"type":"integer"},"type":"array","maxItems":1000,"title":"Mailbox Ids"},"department":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Department","description":"Every assigned mailbox whose employee is in this department."},"all_mailboxes":{"type":"boolean","title":"All Mailboxes","description":"Every active, assigned mailbox.","default":false}},"type":"object","title":"SignatureTemplateTargets","description":"Apply one template across mailboxes. Choose exactly one targeting mode."},"SignatureTemplateWrite":{"properties":{"version":{"type":"integer","title":"Version","description":"Version you last read. Ignored on create.","default":0},"data":{"$ref":"#/components/schemas/SignatureTemplate"}},"type":"object","required":["data"],"title":"SignatureTemplateWrite","description":"Create or update a signature template."},"SignatureVersionResponse":{"properties":{"version":{"type":"integer","title":"Version"}},"type":"object","required":["version"],"title":"SignatureVersionResponse"},"SignerChangeDecisionRequest":{"properties":{"request_id":{"type":"string","maxLength":64,"minLength":8,"title":"Request Id"},"reason":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Reason"}},"type":"object","required":["request_id"],"title":"SignerChangeDecisionRequest","description":"Decide the buyer's pending signer change. Mirrors `SignerChangeDecisionDTO`.\n\n`request_id` comes from the quote detail while a change is pending."},"SignupAttributionRequest":{"properties":{"entry_point":{"anyOf":[{"type":"string","maxLength":50},{"type":"null"}],"title":"Entry Point","description":"Signup entry-point slug."},"utm_source":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Utm Source"},"utm_medium":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Utm Medium"},"utm_campaign":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Utm Campaign"},"utm_term":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Utm Term"},"utm_content":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Utm Content"},"utm_id":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Utm Id"},"gclid":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Gclid"},"wbraid":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Wbraid"},"gbraid":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Gbraid"},"fbclid":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Fbclid"},"landing_page_url":{"anyOf":[{"type":"string","maxLength":2048},{"type":"null"}],"title":"Landing Page Url"},"landing_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Landing At"},"signup_referrer":{"anyOf":[{"type":"string","maxLength":2048},{"type":"null"}],"title":"Signup Referrer"}},"type":"object","title":"SignupAttributionRequest","description":"Mirror of `CaptureAttributionRequest`.\n\nEvery field is optional and every length cap is the app's, so a value this\ncontract accepts is one the handler accepts too."},"SiteConnectionsPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"SiteConnectionsPayload","description":"One handler response. Open-shaped - these payloads come from the tracking pipeline."},"SizeSetRequest":{"properties":{"formats":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":8},{"type":"null"}],"title":"Formats"}},"type":"object","title":"SizeSetRequest","description":"Fan one creative out into the platform's other formats. SPENDS CREDIT.\n\nCopy is locked verbatim; the imagery is re-laid-out per format, so the\ncost scales with how many formats you ask for. Omit `formats` for the\nplatform's full set."},"SkillTestRun":{"properties":{"test_case_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Test Case Id","description":"Run this saved case."},"input_data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Input Data","description":"Ad-hoc inputs (no saved case)."},"expected_output":{"anyOf":[{},{"type":"null"}],"title":"Expected Output","description":"Ad-hoc only: value to assert against."},"assertion_type":{"anyOf":[{"type":"string","enum":["exact","contains","llm_judge"]},{"type":"null"}],"title":"Assertion Type","description":"Ad-hoc only."},"assertion_config":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Assertion Config","description":"Ad-hoc only."},"triggered_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Triggered By","description":"Attribution for the run history."}},"type":"object","title":"SkillTestRun","description":"voice `SkillTestRunRequest`: one dry run, from a saved case OR ad-hoc inputs."},"SkipContactRequest":{"properties":{"contact_id":{"type":"string","title":"Contact Id"}},"type":"object","required":["contact_id"],"title":"SkipContactRequest","description":"Mirrors `DialerSkipContact`. Queue bookkeeping - dials nobody."},"SmsComposeRequest":{"properties":{"from_number":{"type":"string","title":"From Number","description":"A number this organisation owns, E.164."},"to_number":{"type":"string","title":"To Number","description":"The recipient's number, E.164. A real phone."},"body":{"type":"string","title":"Body","description":"Message text."},"save_as_draft":{"type":"boolean","title":"Save As Draft","description":"FALSE SENDS THE MESSAGE. True stores a draft.","default":false},"draft_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Draft Id"},"thread_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Thread Id","description":"Existing SMS thread to continue."}},"type":"object","required":["from_number","to_number","body"],"title":"SmsComposeRequest","description":"Compose an SMS: save it as a draft, or SEND IT TO A REAL PHONE.\n\n`save_as_draft` defaults to FALSE, which means SEND."},"SmsPhoneConfigRequest":{"properties":{"ai_inbox_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Ai Inbox Enabled","description":"Show this number's threads in the inbox"},"auto_respond":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Auto Respond","description":"Let the AI reply on this number"}},"type":"object","title":"SmsPhoneConfigRequest","description":"Partial update of one SMS number's AI-inbox settings.\n\nOmitted fields are left alone; this is a PATCH in PUT's clothing, matching\nthe app exactly rather than inventing a second spelling."},"SnapshotActionResponse":{"properties":{"sandbox":{"type":"boolean","title":"Sandbox","default":true},"action":{"type":"string","title":"Action"},"name":{"type":"string","title":"Name"},"tables":{"items":{"type":"string"},"type":"array","title":"Tables"}},"type":"object","required":["action","name","tables"],"title":"SnapshotActionResponse"},"SnapshotTarget":{"properties":{"kind":{"type":"string","const":"snapshot","title":"Kind","default":"snapshot"},"bucket_end":{"type":"string","format":"date","title":"Bucket End"},"cell":{"type":"string","enum":["all","stage","unstaged","no_history"],"title":"Cell","default":"all"},"stage":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Stage"}},"additionalProperties":false,"type":"object","required":["bucket_end"],"title":"SnapshotTarget","description":"One cell of a stage-over-time report, on the last day of the period that ends on ``bucket_end``: every record\nlive then (``all``), the records in ``stage`` (``stage``), those with no stage (``unstaged``) or those with no\nrecorded stage history (``no_history``)."},"SnippetResponse":{"properties":{"write_key":{"type":"string","title":"Write Key"},"tracking_host":{"type":"string","title":"Tracking Host","default":"https://t.graph8.com"},"domains":{"items":{"type":"string"},"type":"array","title":"Domains"},"react_snippet":{"type":"string","title":"React Snippet","description":"Ready-to-use React component import for @graph8/nextjs"},"script_tag":{"type":"string","title":"Script Tag","description":"Vanilla JS script tag for non-React apps"},"config":{"additionalProperties":true,"type":"object","title":"Config","description":"Full configuration object for gtm/config.json"},"stream_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stream Id","description":"ID of the tracking stream the write key belongs to, when known."},"stream_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stream Name","description":"User-friendly name of that stream, when known."},"stream_selection":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stream Selection","description":"How the stream was chosen: 'explicit' (stream_id given), 'repo_write_key' (the repository's stored key), 'only_stream', 'domain_match' (matches the organization's website), or 'first_stream_fallback' (ambiguous; see action_required)."},"action_required":{"type":"boolean","title":"Action Required","description":"True when the organization has several streams and none could be identified as its main website. The write key is the first stream's (unchanged legacy default); pick the right one from available_streams and call again with stream_id.","default":false},"warning":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Warning","description":"Human-readable explanation when action_required is true, or a stream setup advisory."},"available_streams":{"items":{"$ref":"#/components/schemas/StreamInfoResponse"},"type":"array","title":"Available Streams","description":"The organization's streams to choose from. Filled only when action_required is true."}},"type":"object","required":["write_key","react_snippet","script_tag"],"title":"SnippetResponse"},"SnoozeTaskRequest":{"properties":{"minutes":{"type":"integer","exclusiveMinimum":0.0,"title":"Minutes","description":"Minutes from now to fire the next reminder."}},"type":"object","required":["minutes"],"title":"SnoozeTaskRequest","description":"Push a task's reminder out by N minutes from now."},"SocialAccount":{"properties":{"id":{"type":"string","title":"Id"},"display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display Name"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"profile_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Profile Url"},"provider":{"type":"string","title":"Provider"},"capabilities":{"$ref":"#/components/schemas/SocialCapabilities"},"capacity":{"$ref":"#/components/schemas/SocialAccountCapacity"}},"type":"object","required":["id","provider","capabilities","capacity"],"title":"SocialAccount","description":"A connected social account. `id` is what `account_ref` takes everywhere else."},"SocialAccountCapacity":{"properties":{"publish_used":{"type":"integer","title":"Publish Used"},"publish_limit":{"type":"integer","title":"Publish Limit"}},"type":"object","required":["publish_used","publish_limit"],"title":"SocialAccountCapacity"},"SocialAccountList":{"properties":{"items":{"items":{"$ref":"#/components/schemas/SocialAccount"},"type":"array","title":"Items"}},"type":"object","required":["items"],"title":"SocialAccountList"},"SocialAnalytics":{"properties":{"totals":{"additionalProperties":{"type":"integer"},"type":"object","title":"Totals"},"per_day":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Per Day"}},"type":"object","required":["totals","per_day"],"title":"SocialAnalytics","description":"Totals and a per-day series over the requested window."},"SocialAudienceFromEngagers":{"properties":{"audience_id":{"type":"integer","title":"Audience Id"},"audience_name":{"type":"string","title":"Audience Name"},"added":{"type":"integer","title":"Added"},"matched":{"type":"integer","title":"Matched"},"created":{"type":"integer","title":"Created"},"skipped_no_identity":{"type":"integer","title":"Skipped No Identity"},"truncated":{"type":"boolean","title":"Truncated","default":false}},"type":"object","required":["audience_id","audience_name","added","matched","created","skipped_no_identity"],"title":"SocialAudienceFromEngagers","description":"The audience built from a post's engagers."},"SocialAudienceFromEngagersRequest":{"properties":{"audience_name":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Audience Name"}},"type":"object","title":"SocialAudienceFromEngagersRequest","description":"Build an audience from the people who engaged with a post."},"SocialAutopilot":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"account_ref":{"type":"string","title":"Account Ref"},"configured":{"type":"boolean","title":"Configured","default":true},"available":{"type":"boolean","title":"Available"},"direction":{"type":"string","title":"Direction","default":""},"timezone":{"type":"string","title":"Timezone","default":"UTC"},"weekly_queue_slots":{"items":{"$ref":"#/components/schemas/SocialQueueSlot"},"type":"array","title":"Weekly Queue Slots"},"enabled":{"type":"boolean","title":"Enabled","default":false},"auto_publish_confirmed":{"type":"boolean","title":"Auto Publish Confirmed","default":false},"prompt_version":{"type":"integer","title":"Prompt Version","default":1},"last_planned_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Planned At"},"last_blocking_error":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Blocking Error"},"next_slots":{"items":{"type":"string"},"type":"array","title":"Next Slots"},"scheduled_count":{"type":"integer","title":"Scheduled Count","default":0},"estimated_generation_credits":{"type":"integer","title":"Estimated Generation Credits","default":0},"unscheduled_posts":{"type":"integer","title":"Unscheduled Posts","default":0}},"type":"object","required":["account_ref","available"],"title":"SocialAutopilot","description":"Autopilot configuration and state for one account."},"SocialAutopilotSaveRequest":{"properties":{"direction":{"type":"string","maxLength":2000,"minLength":1,"title":"Direction","description":"What autopilot should post about."},"timezone":{"type":"string","maxLength":64,"minLength":1,"title":"Timezone","description":"IANA timezone."},"weekly_queue_slots":{"items":{"$ref":"#/components/schemas/SocialQueueSlot"},"type":"array","maxItems":14,"minItems":1,"title":"Weekly Queue Slots"},"enabled":{"type":"boolean","title":"Enabled","default":false},"auto_publish_confirmed":{"type":"boolean","title":"Auto Publish Confirmed","description":"True lets autopilot PUBLISH what it writes without a human approving each post.","default":false}},"type":"object","required":["direction","timezone","weekly_queue_slots"],"title":"SocialAutopilotSaveRequest","description":"Configure autopilot for one account."},"SocialCapabilities":{"properties":{"publish_personal":{"type":"boolean","title":"Publish Personal"},"publish_company":{"type":"boolean","title":"Publish Company"},"analytics":{"type":"boolean","title":"Analytics"},"leads":{"type":"boolean","title":"Leads"},"media":{"type":"boolean","title":"Media"}},"type":"object","required":["publish_personal","publish_company","analytics","leads","media"],"title":"SocialCapabilities","description":"What an account's connection can do."},"SocialCollection":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"SocialCollection","description":"A list of social-listening objects. A bare list is surfaced as `items`;\na named collection keeps its key AND gains `items`."},"SocialDeleted":{"properties":{"deleted":{"type":"boolean","title":"Deleted","default":true}},"type":"object","title":"SocialDeleted","description":"The resource is gone."},"SocialEngager":{"properties":{"name":{"type":"string","title":"Name"},"headline":{"type":"string","title":"Headline","default":""},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url"},"action":{"type":"string","title":"Action"},"contact_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Contact Id"},"resolution":{"type":"string","title":"Resolution"}},"type":"object","required":["name","action","resolution"],"title":"SocialEngager","description":"One person who engaged with a post."},"SocialEngagers":{"properties":{"items":{"items":{"$ref":"#/components/schemas/SocialEngager"},"type":"array","title":"Items"},"total":{"type":"integer","title":"Total"},"supported":{"type":"boolean","title":"Supported","default":true},"truncated":{"type":"boolean","title":"Truncated","default":false}},"type":"object","required":["items","total"],"title":"SocialEngagers","description":"Engagers of a post. `truncated: true` means this is a PARTIAL list."},"SocialEnrollEngagersRequest":{"properties":{"sequence_id":{"type":"string","minLength":1,"title":"Sequence Id"},"contact_ids":{"items":{"type":"integer"},"type":"array","minItems":1,"title":"Contact Ids","description":"`contact_id`s from the post's engagers."}},"type":"object","required":["sequence_id","contact_ids"],"title":"SocialEnrollEngagersRequest","description":"Enroll chosen engagers of a post into a sequence."},"SocialEnrollResult":{"properties":{"enrolled":{"type":"integer","title":"Enrolled"},"audience_id":{"type":"integer","title":"Audience Id"},"sequence_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Status"}},"type":"object","required":["enrolled","audience_id"],"title":"SocialEnrollResult","description":"Engagers enrolled into a sequence."},"SocialGenerated":{"properties":{"variants":{"items":{"$ref":"#/components/schemas/SocialVariant"},"type":"array","title":"Variants"},"credits_used":{"type":"integer","title":"Credits Used"},"provenance":{"items":{"type":"string"},"type":"array","title":"Provenance"}},"type":"object","required":["variants","credits_used","provenance"],"title":"SocialGenerated","description":"Generated drafts. Nothing has been saved."},"SocialGenerationContext":{"properties":{"brand_voice":{"type":"boolean","title":"Brand Voice"},"campaign_brief":{"type":"boolean","title":"Campaign Brief"},"proof_points":{"type":"integer","title":"Proof Points"},"inbox_insights":{"type":"integer","title":"Inbox Insights"},"recent_content":{"type":"integer","title":"Recent Content"},"top_posts":{"type":"integer","title":"Top Posts"}},"type":"object","required":["brand_voice","campaign_brief","proof_points","inbox_insights","recent_content","top_posts"],"title":"SocialGenerationContext","description":"Which grounding sources have data to draw on."},"SocialIdea":{"properties":{"id":{"type":"string","title":"Id"},"title":{"type":"string","title":"Title"},"concept":{"type":"string","title":"Concept","default":""},"why":{"type":"string","title":"Why","default":""},"primary_hook":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Primary Hook"},"secondary_hooks":{"items":{"type":"string"},"type":"array","title":"Secondary Hooks"},"proof_points":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Proof Points"},"source":{"type":"string","title":"Source"},"receipts":{"items":{"$ref":"#/components/schemas/SocialIdeaReceipt"},"type":"array","title":"Receipts"},"fit":{"$ref":"#/components/schemas/SocialIdeaFit"},"favorited":{"type":"boolean","title":"Favorited","default":false},"drafted_count":{"type":"integer","title":"Drafted Count","default":0},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"}},"type":"object","required":["id","title","source","fit"],"title":"SocialIdea","description":"One post idea."},"SocialIdeaFit":{"properties":{"grade":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Grade"},"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason"}},"type":"object","title":"SocialIdeaFit"},"SocialIdeaReceipt":{"properties":{"kind":{"type":"string","title":"Kind"},"count":{"type":"integer","title":"Count"}},"type":"object","required":["kind","count"],"title":"SocialIdeaReceipt"},"SocialIdeas":{"properties":{"items":{"items":{"$ref":"#/components/schemas/SocialIdea"},"type":"array","title":"Items"},"sources":{"additionalProperties":{"type":"integer"},"type":"object","title":"Sources"}},"type":"object","required":["items","sources"],"title":"SocialIdeas","description":"Post ideas, plus how many came from each source."},"SocialMediaItem":{"properties":{"kind":{"type":"string","title":"Kind","description":"Asset kind. `image` for a picture.","default":"image"},"url":{"type":"string","title":"Url","description":"Publicly fetchable URL of the asset."},"alt":{"type":"string","title":"Alt","description":"Alt text. `alt_text` is accepted as a synonym.","default":""},"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id","description":"Asset-library id, when the asset came from there."}},"type":"object","required":["url"],"title":"SocialMediaItem","description":"One image (or other asset) attached to a post."},"SocialPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"SocialPayload","description":"One social-listening object, or one handler response.\n\nOpen-shaped: these payloads carry per-platform detail that differs between\nX, LinkedIn, Reddit, Instagram and YouTube and grows with them."},"SocialPost":{"properties":{"id":{"type":"string","title":"Id"},"provider":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Provider"},"account_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Ref"},"body":{"type":"string","title":"Body"},"media":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Media"},"post_type":{"type":"string","title":"Post Type"},"status":{"type":"string","title":"Status"},"scheduled_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Scheduled At"},"published_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Published At"},"external_post_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"External Post Id"},"external_post_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"External Post Url"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id"},"idea_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Idea Id"},"generation_sources":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Generation Sources"},"autopilot_config_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Autopilot Config Id"},"autopilot_version":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Autopilot Version"},"generation_metadata":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Generation Metadata"},"created_by":{"type":"string","title":"Created By"},"failure_reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Failure Reason"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["id","body","post_type","status","created_by"],"title":"SocialPost","description":"One post."},"SocialPostCreateRequest":{"properties":{"account_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Ref","description":"The account it will publish from - an `id` from `GET /social/accounts`. Optional: a draft can be written before any account is connected, but one is required to schedule or publish."},"body":{"type":"string","maxLength":3000,"minLength":1,"title":"Body","description":"The post text."},"media":{"anyOf":[{"items":{"$ref":"#/components/schemas/SocialMediaItem"},"type":"array","maxItems":9},{"type":"null"}],"title":"Media"},"post_type":{"type":"string","enum":["text","image","video","document"],"title":"Post Type","default":"text"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id","description":"Campaign to attribute the post to."},"idempotency_key":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Idempotency Key","description":"Repeat a create with the same key to get the original post back instead of a duplicate."},"idea_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Idea Id","description":"The idea from `GET /social/ideas` this came from."},"generation_sources":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":10},{"type":"null"}],"title":"Generation Sources"}},"type":"object","required":["body"],"title":"SocialPostCreateRequest","description":"A new post. Created as a DRAFT - nothing is published until you schedule or publish it."},"SocialPostGenerateRequest":{"properties":{"instructions":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Instructions"},"context":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Context","description":"Older synonym of `instructions`."},"idea_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Idea Id"},"sources":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":6},{"type":"null"}],"title":"Sources","description":"Grounding sources. Omit for the default set (brand_voice, campaign_brief, proof_catalog, inbox_insights). `GET /social/generate/context` says which have data."},"tone":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Tone"},"frame":{"anyOf":[{"type":"string","maxLength":40},{"type":"null"}],"title":"Frame"},"variants":{"type":"integer","maximum":3.0,"minimum":1.0,"title":"Variants","default":3},"hashtags_max":{"type":"integer","maximum":3.0,"minimum":0.0,"title":"Hashtags Max","default":3},"refine":{"anyOf":[{"$ref":"#/components/schemas/SocialRefineSpec"},{"type":"null"}]},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id"},"reference_post":{"anyOf":[{"type":"string","maxLength":4000},{"type":"null"}],"title":"Reference Post","description":"Someone else's post, used as a structural template only."}},"type":"object","title":"SocialPostGenerateRequest","description":"Ask the AI studio for draft variants. SPENDS CREDITS; saves nothing.\n\nThe variants come back in the response - create a post from the one you\nwant with `POST /social/posts`."},"SocialPostMetrics":{"properties":{"impressions":{"type":"integer","title":"Impressions","default":0},"reactions":{"type":"integer","title":"Reactions","default":0},"comments":{"type":"integer","title":"Comments","default":0},"shares":{"type":"integer","title":"Shares","default":0},"fetched_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Fetched At"},"supported":{"type":"boolean","title":"Supported","default":true}},"type":"object","title":"SocialPostMetrics","description":"Engagement on a published post. `supported: false` means the zeros are placeholders, not measurements."},"SocialPostPage":{"properties":{"items":{"items":{"$ref":"#/components/schemas/SocialPost"},"type":"array","title":"Items"},"total":{"type":"integer","title":"Total"},"counts":{"additionalProperties":{"type":"integer"},"type":"object","title":"Counts"}},"type":"object","required":["items","total","counts"],"title":"SocialPostPage","description":"A page of posts plus the org-wide count per status."},"SocialPostScheduleRequest":{"properties":{"scheduled_at":{"type":"string","format":"date-time","title":"Scheduled At","description":"ISO 8601. Include a timezone offset."}},"type":"object","required":["scheduled_at"],"title":"SocialPostScheduleRequest","description":"When to publish."},"SocialPostUpdateRequest":{"properties":{"body":{"anyOf":[{"type":"string","maxLength":3000},{"type":"null"}],"title":"Body"},"media":{"anyOf":[{"items":{"$ref":"#/components/schemas/SocialMediaItem"},"type":"array","maxItems":9},{"type":"null"}],"title":"Media"},"post_type":{"anyOf":[{"type":"string","enum":["text","image","video","document"]},{"type":"null"}],"title":"Post Type"},"account_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Ref"}},"type":"object","title":"SocialPostUpdateRequest","description":"Edit a post. Only the fields you send change.\n\n`account_ref: null` sent EXPLICITLY detaches the draft from its account;\nomitting the field leaves the account alone."},"SocialProvider":{"properties":{"key":{"type":"string","title":"Key"},"label":{"type":"string","title":"Label"},"description":{"type":"string","title":"Description"},"connect_method":{"type":"string","title":"Connect Method"},"available":{"type":"boolean","title":"Available"},"capabilities":{"$ref":"#/components/schemas/SocialCapabilities"}},"type":"object","required":["key","label","description","connect_method","available","capabilities"],"title":"SocialProvider","description":"A way of connecting an account."},"SocialProviderList":{"properties":{"items":{"items":{"$ref":"#/components/schemas/SocialProvider"},"type":"array","title":"Items"}},"type":"object","required":["items"],"title":"SocialProviderList"},"SocialPublishAccepted":{"properties":{"status":{"type":"string","title":"Status"},"post":{"$ref":"#/components/schemas/SocialPost"}},"type":"object","required":["status","post"],"title":"SocialPublishAccepted","description":"Publishing was queued. `status` is the post's state right now - `scheduled` until the publisher claims it."},"SocialQueueSlot":{"properties":{"day":{"type":"integer","maximum":6.0,"minimum":0.0,"title":"Day","description":"0 = Monday ... 6 = Sunday."},"time":{"type":"string","pattern":"^\\d{2}:\\d{2}$","title":"Time","description":"HH:MM in the autopilot's timezone."}},"type":"object","required":["day","time"],"title":"SocialQueueSlot","description":"A weekly publishing slot."},"SocialRefineSpec":{"properties":{"body":{"type":"string","maxLength":3000,"minLength":1,"title":"Body"},"instruction":{"type":"string","maxLength":300,"minLength":1,"title":"Instruction"}},"type":"object","required":["body","instruction"],"title":"SocialRefineSpec","description":"Rewrite an existing draft instead of generating from scratch."},"SocialVariant":{"properties":{"frame":{"type":"string","title":"Frame"},"body":{"type":"string","title":"Body"}},"type":"object","required":["frame","body"],"title":"SocialVariant","description":"One generated draft."},"SoulCaptureRequest":{"properties":{"org_soul":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Org Soul","description":"Who the organisation is."},"org_memory":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Org Memory","description":"Durable org-level facts."},"user_memory":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Memory","description":"Durable facts about this person."}},"type":"object","title":"SoulCaptureRequest","description":"Mirror of `SoulCaptureRequest`.\n\nEvery field optional: this is used to fill in whichever of the three\ndocuments the caller has, and sending one does not clear the others."},"SourceCompanyDto":{"properties":{"company_id":{"type":"integer","title":"Company Id"},"company_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Name"},"company_domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Domain"}},"type":"object","required":["company_id"],"title":"SourceCompanyDto","description":"A company the imported contacts are attributed back to."},"SourceInput":{"properties":{"resource":{"type":"string","maxLength":1000,"minLength":1,"title":"Resource"},"title":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Title"},"checksum":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Checksum"},"locator":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Locator"}},"type":"object","required":["resource"],"title":"SourceInput","description":"A citation behind an authored concept."},"SsoEnforcementRequest":{"properties":{"require_sso":{"type":"boolean","title":"Require Sso","description":"True makes SSO the only way in. Defaults to false, as the app's does.","default":false},"grant_ttl_minutes":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Grant Ttl Minutes","description":"How long an SSO grant stays valid."},"allow_unverified_domain_members":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Allow Unverified Domain Members","description":"Whether members on an unverified email domain may still sign in."},"allowed_domains":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Allowed Domains"}},"type":"object","title":"SsoEnforcementRequest","description":"Whether SSO is the only way in, and on what terms.\n\n`require_sso: true` blocks every other sign-in method. Do it only once you\nhave signed in through SSO yourself."},"Stage":{"properties":{"from_month":{"type":"integer","minimum":1.0,"title":"From Month","default":1},"through_month":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Through Month"},"percentage":{"anyOf":[{"type":"number","maximum":100.0,"minimum":0.0},{"type":"string"}],"title":"Percentage","default":"0"},"fixed_amount":{"anyOf":[{"type":"number","minimum":0.0},{"type":"string"}],"title":"Fixed Amount","default":"0"},"quality_percentage":{"anyOf":[{"type":"number","maximum":100.0,"minimum":0.0},{"type":"string"}],"title":"Quality Percentage","default":"0"}},"additionalProperties":false,"type":"object","title":"Stage"},"StageBackfillRequest":{"properties":{"confirm":{"type":"boolean","title":"Confirm","description":"Must be true. The app refuses the call with 400 otherwise - a deliberate second hand on a job that spends credits."},"max_credits":{"type":"integer","minimum":0.0,"title":"Max Credits","description":"Hard credit ceiling for this job. The worker stops when spend reaches it. REQUIRED - there is no default, because a default would be a number nobody chose."}},"type":"object","required":["confirm","max_credits"],"title":"StageBackfillRequest","description":"Start a stage-document backfill. SPENDS CREDITS.\n\n`max_credits` is a REAL ceiling, not a hint: the worker stops the job the\nmoment `credits_used >= credits_cap`. Call the estimate first and set it\nfrom the figure you get back."},"StageCreateRequest":{"properties":{"name":{"type":"string","title":"Name"},"probability":{"type":"integer","title":"Probability","default":0},"stage_type":{"type":"string","title":"Stage Type","default":"open"},"color":{"type":"string","title":"Color","default":"#6B7280"},"required_elements":{"items":{"type":"string"},"type":"array","title":"Required Elements"},"recommended_elements":{"items":{"type":"string"},"type":"array","title":"Recommended Elements"},"channel_scripts":{"anyOf":[{"additionalProperties":{"type":"string"},"type":"object"},{"type":"null"}],"title":"Channel Scripts"}},"type":"object","required":["name"],"title":"StageCreateRequest"},"StageDocSlotPatchRequest":{"properties":{"auto_generate":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Auto Generate"},"docs":{"anyOf":[{"items":{"$ref":"#/components/schemas/StageDocSpecRequest"},"type":"array"},{"type":"null"}],"title":"Docs"},"on_demand":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"On Demand"},"credit_cap":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Credit Cap"},"top_n_contacts":{"anyOf":[{"type":"integer","maximum":100.0,"minimum":1.0},{"type":"null"}],"title":"Top N Contacts"},"reuse_if_fresh_days":{"anyOf":[{"type":"integer","maximum":365.0,"minimum":0.0},{"type":"null"}],"title":"Reuse If Fresh Days"}},"type":"object","title":"StageDocSlotPatchRequest","description":"Merge-update for ONE (stage, entity) document slot.\n\nEvery field is optional and only the ones you SEND are applied - but note\nthe app drops `None` values from the patch rather than writing them, so a\nfield cannot be cleared by sending null. Send the value you want instead."},"StageDocSpecRequest":{"properties":{"type":{"type":"string","maxLength":100,"minLength":1,"title":"Type"},"tier":{"type":"string","maxLength":32,"minLength":1,"title":"Tier","default":"sonnet"},"mandatory":{"type":"boolean","title":"Mandatory","default":false},"trigger":{"type":"string","enum":["instant","scheduled"],"title":"Trigger","default":"instant"},"schedule":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Schedule"}},"type":"object","required":["type"],"title":"StageDocSpecRequest"},"StageReorderRequest":{"properties":{"stage_ids":{"items":{"type":"string"},"type":"array","title":"Stage Ids"}},"type":"object","required":["stage_ids"],"title":"StageReorderRequest"},"StageTarget":{"properties":{"kind":{"type":"string","const":"stage","title":"Kind","default":"stage"},"stage":{"type":"string","maxLength":500,"minLength":1,"title":"Stage"}},"additionalProperties":false,"type":"object","required":["stage"],"title":"StageTarget","description":"One stage of a funnel or time-in-stage report."},"StageUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"probability":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Probability"},"stage_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage Type"},"color":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Color"},"required_elements":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Required Elements"},"recommended_elements":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Recommended Elements"},"channel_scripts":{"anyOf":[{"additionalProperties":{"type":"string"},"type":"object"},{"type":"null"}],"title":"Channel Scripts"}},"type":"object","title":"StageUpdateRequest"},"StagegateAttestationRequest":{"properties":{"evidence_key":{"type":"string","enum":["pain_identified","impact_quantified","stakeholder_mapped","decision_process_known","timeline_known","commercial_posture_known","next_step_scheduled","risk_or_blocker_logged"],"title":"Evidence Key"},"note":{"type":"string","maxLength":2000,"title":"Note","description":"How it was covered. Required."}},"additionalProperties":false,"type":"object","required":["evidence_key","note"],"title":"StagegateAttestationRequest"},"StagegateBacktestPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"StagegateBacktestPayload","description":"A rule's backtest verdict against closed deals, or every rule ranked by win-rate gap."},"StagegateBacktestPreviewRequest":{"properties":{"window_days":{"type":"integer","enum":[90,180,365],"title":"Window Days","description":"Closed deals from this many days back.","default":180},"conditions":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Conditions"},"pipeline_ids":{"anyOf":[{"items":{"type":"string","format":"uuid"},"type":"array"},{"type":"null"}],"title":"Pipeline Ids"}},"additionalProperties":false,"type":"object","required":["conditions"],"title":"StagegateBacktestPreviewRequest"},"StagegateBacktestRequest":{"properties":{"window_days":{"type":"integer","enum":[90,180,365],"title":"Window Days","description":"Closed deals from this many days back.","default":180}},"additionalProperties":false,"type":"object","title":"StagegateBacktestRequest"},"StagegateDealPanelPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"StagegateDealPanelPayload","description":"One deal's open violations and evidence (`violations`, `crm_provider`, `can_snooze`)."},"StagegateFeedbackPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"StagegateFeedbackPayload","description":"The acknowledgement of a \"this is wrong\" report or a verdict rating."},"StagegatePackInstallRequest":{"properties":{"pipeline_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Pipeline Id"},"stage_map":{"anyOf":[{"additionalProperties":{"type":"string"},"type":"object"},{"type":"null"}],"title":"Stage Map","description":"Pack slot to stage id."},"rule_keys":{"items":{"type":"string"},"type":"array","maxItems":200,"minItems":1,"title":"Rule Keys"},"enabled":{"type":"boolean","title":"Enabled","default":true}},"additionalProperties":false,"type":"object","required":["rule_keys"],"title":"StagegatePackInstallRequest"},"StagegatePackPreviewRequest":{"properties":{"pipeline_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Pipeline Id"},"stage_map":{"anyOf":[{"additionalProperties":{"type":"string"},"type":"object"},{"type":"null"}],"title":"Stage Map","description":"Pack slot to stage id."}},"additionalProperties":false,"type":"object","title":"StagegatePackPreviewRequest"},"StagegatePacksPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"StagegatePacksPayload","description":"Template pack cards, a pack bound to a pipeline, or the result of installing one."},"StagegateQuickFixRequest":{"properties":{"violation_id":{"type":"string","format":"uuid","title":"Violation Id"},"quick_fix_kind":{"type":"string","enum":["note","task","call","meeting"],"title":"Quick Fix Kind"}},"additionalProperties":false,"type":"object","required":["violation_id","quick_fix_kind"],"title":"StagegateQuickFixRequest","description":"Which quick fix led to this recheck; optional on the recheck call."},"StagegateRatingRequest":{"properties":{"rating":{"type":"string","enum":["up","down"],"title":"Rating"},"verdict":{"type":"string","enum":["hurts_win_rate","no_effect","flagged_win_more","not_enough_data","hidden"],"title":"Verdict"},"window_days":{"type":"integer","enum":[90,180,365],"title":"Window Days"},"rule_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Rule Id","description":"Rate a saved rule's verdict, or ..."},"conditions":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Conditions","description":"... a draft's, by its conditions."},"pipeline_ids":{"anyOf":[{"items":{"type":"string","format":"uuid"},"type":"array"},{"type":"null"}],"title":"Pipeline Ids"}},"additionalProperties":false,"type":"object","required":["rating","verdict","window_days"],"title":"StagegateRatingRequest"},"StagegateRuleRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":200,"minLength":1},{"type":"null"}],"title":"Name"},"conditions":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Conditions","description":"The rule logic; the app validates the condition types."},"how_to_fix":{"anyOf":[{"type":"string","maxLength":4000},{"type":"null"}],"title":"How To Fix"},"quick_fix_kind":{"anyOf":[{"type":"string","enum":["note","task","call","meeting"]},{"type":"null"}],"title":"Quick Fix Kind"},"pipeline_ids":{"anyOf":[{"items":{"type":"string","format":"uuid"},"type":"array"},{"type":"null"}],"title":"Pipeline Ids","description":"Only deals in these pipelines; omit for all."},"enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Enabled"}},"additionalProperties":false,"type":"object","title":"StagegateRuleRequest","description":"A rule. For PATCH send only the fields to change; POST needs `name` and `conditions`."},"StagegateRulesPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"StagegateRulesPayload","description":"The organisation's rules (`items`, `can_edit`, `reconciled`) or one rule."},"StagegateSettingsPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"StagegateSettingsPayload","description":"Escalation and grace settings plus the organisation time zone."},"StagegateSettingsRequest":{"properties":{"escalate_after_days":{"type":"integer","maximum":30.0,"minimum":1.0,"title":"Escalate After Days"},"grace_days":{"type":"integer","maximum":14.0,"minimum":0.0,"title":"Grace Days"}},"additionalProperties":false,"type":"object","required":["escalate_after_days","grace_days"],"title":"StagegateSettingsRequest"},"StagegateSnoozeRequest":{"properties":{"until":{"type":"string","format":"date","title":"Until","description":"Wake on this date (organisation time): after today, within the app's limit."},"reason":{"type":"string","maxLength":500,"title":"Reason"}},"additionalProperties":false,"type":"object","required":["until","reason"],"title":"StagegateSnoozeRequest"},"StagegateViewPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"StagegateViewPayload","description":"A board, queue, attention list, trend, ranking or status read."},"StagegateWrongRequest":{"properties":{"reason":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Reason"}},"additionalProperties":false,"type":"object","title":"StagegateWrongRequest"},"StagingPromptGeneratorRequest":{"properties":{"task_description":{"type":"string","minLength":1,"title":"Task Description","description":"What the AI pass should do, in plain words."}},"type":"object","required":["task_description"],"title":"StagingPromptGeneratorRequest","description":"Ask the model to write a prompt from the table's columns and sample rows."},"StagingRowsQueryRequest":{"properties":{"start_row":{"type":"integer","maximum":100000.0,"minimum":0.0,"title":"Start Row","default":0},"end_row":{"type":"integer","maximum":100000.0,"minimum":1.0,"title":"End Row","default":100},"filter_model":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Filter Model"},"sort_model":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Sort Model"}},"type":"object","title":"StagingRowsQueryRequest","description":"Read a window of rows. Reads only - nothing is enriched or charged."},"StartCrawlRequest":{"properties":{"max_pages":{"anyOf":[{"type":"integer","maximum":5000.0,"minimum":10.0},{"type":"null"}],"title":"Max Pages"},"source_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Url","description":"Where to start. Omit to use the org's configured site."}},"type":"object","title":"StartCrawlRequest","description":"Crawl a whole site. Long-running, and it fetches every reachable page."},"StartDiscoveryRequest":{"properties":{"connection_id":{"type":"string","title":"Connection Id"},"crm_type":{"type":"string","title":"Crm Type","description":"Which CRM. The app's default is `hubspot`.","default":"hubspot"}},"type":"object","required":["connection_id"],"title":"StartDiscoveryRequest","description":"Look at what is in the CRM. Reads the CRM, writes nothing to graph8.\n\nDiscovery is the first half of a migration: it counts records, reads the\nfield and pipeline shape, and proposes mappings. Nothing is imported until\n`confirm-and-start`."},"StartParallelSessionRequest":{"properties":{"user_id":{"type":"string","title":"User Id"},"user_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Email"},"contacts":{"items":{"$ref":"#/components/schemas/DialContact"},"type":"array","title":"Contacts"},"from_phone":{"type":"string","title":"From Phone"},"session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Id"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id"},"campaign_builder_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Builder Campaign Id"},"session_metadata":{"anyOf":[{"$ref":"#/components/schemas/SessionMetadataIn"},{"type":"null"}]},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"}},"type":"object","required":["user_id","contacts","from_phone"],"title":"StartParallelSessionRequest","description":"Mirrors `ParallelDialRequest` minus `org_id`. THIS DIALS EVERY CONTACT."},"StatementCreateRequest":{"properties":{"engagement_id":{"type":"string","title":"Engagement Id","description":"The hiring/engagement to bill. Must be your own."},"period_start":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"Period Start","description":"IGNORED - the period is server-derived."},"period_end":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"Period End","description":"IGNORED - the period is server-derived."},"summary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Summary"},"activities":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Activities"},"amount":{"anyOf":[{"type":"number"},{"type":"string"},{"type":"null"}],"title":"Amount","description":"IGNORED - derived from the line items."},"currency":{"type":"string","maxLength":3,"title":"Currency","default":"USD"}},"type":"object","required":["engagement_id"],"title":"StatementCreateRequest","description":"Open a draft statement for one engagement.\n\n`period_start` / `period_end` / `amount` are accepted for parity with the\napp model and IGNORED by it. The billing period is derived server-side (the\nprevious complete calendar month, or a terminated engagement's earliest\nunbilled month) so nobody can pick a window that mis-prorates the retainer,\nand the amount is the sum of the statement's line items. They are documented\nas ignored rather than dropped from the contract, because dropping a field\nthe app model declares is what makes a proxy 500 on a required one."},"StatementDecisionRequest":{"properties":{"reason":{"type":"string","maxLength":2000,"minLength":1,"title":"Reason"}},"type":"object","required":["reason"],"title":"StatementDecisionRequest","description":"The client's reason when returning a statement to its author."},"StatementUpdateRequest":{"properties":{"summary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Summary"},"activities":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Activities"},"amount":{"anyOf":[{"type":"number","exclusiveMinimum":0.0},{"type":"string"},{"type":"null"}],"title":"Amount","description":"IGNORED by the update whitelist."},"period_start":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"Period Start","description":"IGNORED by the update whitelist."},"period_end":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"Period End","description":"IGNORED by the update whitelist."}},"type":"object","title":"StatementUpdateRequest","description":"Edit a draft's free text. Only `summary` and `activities` take effect.\n\n`amount` and the period are not editable by anyone, on either the talent or\nthe agency path - they are the base-pay levers the create path deliberately\ncloses. They stay on the model only because the app model still declares\nthem."},"StepConfig":{"properties":{"step_order":{"type":"integer","title":"Step Order","description":"Order of the step in the sequence (1-based)"},"step_type":{"type":"string","title":"Step Type","description":"Step type. One of: EMAIL, PHONE, SMS, WHATSAPP, HEYREACH, MANUAL_DIALER. Note: LinkedIn outreach uses HEYREACH (not LINKEDIN). Case-insensitive aliases accepted."},"input_type":{"type":"string","title":"Input Type","description":"Input type. One of: ON_DEMAND, MANUAL_TEMPLATE, AI_GENERATED_TEMPLATE. Case-insensitive aliases accepted (e.g. 'template' -> MANUAL_TEMPLATE, 'ai' -> AI_GENERATED_TEMPLATE).","default":"ON_DEMAND"},"time_interval":{"type":"integer","title":"Time Interval","description":"Delay in seconds after the previous step","default":0},"step_data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Step Data","description":"Step template/content data (subject, body, instructions, etc.)"}},"type":"object","required":["step_order","step_type"],"title":"StepConfig"},"StepUpdateRequest":{"properties":{"step_data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Step Data","description":"Step template/content data"},"time_interval":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Time Interval","description":"Delay in seconds after the previous step"},"step_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Step Type","description":"Step type. One of: EMAIL, PHONE, SMS, WHATSAPP, HEYREACH, MANUAL_DIALER. Case-insensitive."},"input_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Input Type","description":"Input type. One of: ON_DEMAND, MANUAL_TEMPLATE, AI_GENERATED_TEMPLATE. Case-insensitive."}},"type":"object","title":"StepUpdateRequest"},"StreamInfoResponse":{"properties":{"id":{"type":"string","title":"Id","description":"Stream ID used to select this stream"},"name":{"type":"string","title":"Name","description":"User-friendly stream name (e.g. 'graph8.com', 'heyreach-graph8')"},"domains":{"items":{"type":"string"},"type":"array","title":"Domains","description":"Domains associated with this stream"},"write_key":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Write Key","description":"Public write key for this stream"},"repo_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Repo Id","description":"Connected repository whose stored write key belongs to this stream. Null when no connected repository uses it: streams are organization-level, not owned by a repo."},"is_default":{"type":"boolean","title":"Is Default","description":"True for the stream GET /snippet uses when no stream_id is given: the only stream, or the one whose domain matches the organization's website. False on every stream when that choice is ambiguous; pass stream_id explicitly then.","default":false},"domains_restricted":{"type":"boolean","title":"Domains Restricted","description":"Whether the stream lists allowed domains. False means its public write key is accepted from any website (see warning).","default":false},"warning":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Warning","description":"Read-only advisory about this stream's setup, e.g. no allowed domains. Nothing is enforced."}},"type":"object","required":["id","name"],"title":"StreamInfoResponse"},"StripeApiKeyRequest":{"properties":{"api_key":{"type":"string","minLength":10,"title":"Api Key","description":"Stripe restricted or secret key: rk_live_, rk_test_, sk_live_ or sk_test_."}},"type":"object","required":["api_key"],"title":"StripeApiKeyRequest","description":"Connect Stripe with a restricted (or secret) API key.\n\nWRITE-ONLY: the key is stored encrypted and never returned by any operation."},"StudioContentListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"StudioContentListPayload","description":"A LIST result, open-shaped, with `items` always present.\n\nThe app returns a bare list from some routes and a named key from others\n(`pages`, `grids`, `images`, `creatives`, `reports`, `items`). Both are\npublished: the original key is preserved AND mirrored onto `items`, so a\nclient can page any Studio collection the same way without a per-route\nlookup table."},"StudioContentPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"StudioContentPayload","description":"One Studio object, open-shaped. See the module docstring."},"StudioListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"StudioListPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape.\n\nA handler that returns `[...]` and one that returns `{\"documents\": [...]}`\nboth land on `items`, and the named key is preserved beside it so a caller\nreading the app's own spelling is not broken by the normalisation."},"StudioPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"StudioPayload","description":"An open envelope for one settings block, document or brand artefact.\n\nOPEN on purpose. These surfaces are configuration and generated content,\nand both grow: a new toggle on a settings block or a new field on a\ngenerated document must reach a caller on the day it ships, not on the day\nsomebody remembers to widen a mirror. A closed response model here would\nsilently DROP the new key, which reads to the caller as \"the product does\nnot have that setting\".\n\nThe request side is the opposite and is mirrored exactly - see the module\ndocstring for why the asymmetry is deliberate."},"StyleNormalizeRequest":{"properties":{"text":{"type":"string","title":"Text"}},"type":"object","required":["text"],"title":"StyleNormalizeRequest","description":"Text to normalise to the org's writing style."},"SubCalendarResponse":{"properties":{"external_id":{"type":"string","title":"External Id"},"name":{"type":"string","title":"Name"},"is_selected":{"type":"boolean","title":"Is Selected","default":false},"is_primary":{"type":"boolean","title":"Is Primary","default":false},"read_only":{"type":"boolean","title":"Read Only","default":false}},"type":"object","required":["external_id","name"],"title":"SubCalendarResponse"},"SubmitInvoiceRequest":{"properties":{"hiring_id":{"type":"string","title":"Hiring Id"},"period_start":{"type":"string","title":"Period Start","description":"YYYY-MM-DD"},"period_end":{"type":"string","title":"Period End","description":"YYYY-MM-DD"}},"type":"object","required":["hiring_id","period_start","period_end"],"title":"SubmitInvoiceRequest"},"SubmitScrapeRequest":{"properties":{"requirement":{"type":"string","maxLength":2000,"minLength":3,"title":"Requirement","description":"What to scrape, in plain English."},"staging_table_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Staging Table Id","description":"Staging table to read from and write into."},"source_column":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Column","description":"Column holding the values to scrape from."},"seed_targets":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Seed Targets","description":"Cold start: add these as rows in `source_column` before scraping."},"row_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Row Ids","description":"Limit the run to these rows. Omit it to run every row; an empty list is rejected."},"adapter":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Adapter","description":"Skip the planner and use this capability directly."},"rescrape":{"type":"boolean","title":"Rescrape","description":"Re-run rows that already have a result.","default":false},"params":{"additionalProperties":true,"type":"object","title":"Params"},"preview":{"type":"boolean","title":"Preview","description":"Hold the run behind a 5-row preview. Leave it on for a first run.","default":true}},"type":"object","required":["requirement"],"title":"SubmitScrapeRequest","description":"Ask for a scrape, in plain English.\n\n`preview` defaults to TRUE and that default is load-bearing: it holds the\nrun behind a five-row sample so you can see what it will do before it does\nit at scale. Turning it off is what makes a run expensive."},"SubscriberAddRequest":{"properties":{"email":{"type":"string","maxLength":255,"title":"Email"},"first_name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Last Name"}},"type":"object","required":["email"],"title":"SubscriberAddRequest"},"SubscriberListResponse":{"properties":{"items":{"items":{"$ref":"#/components/schemas/SubscriberSummary"},"type":"array","title":"Items"},"total":{"type":"integer","title":"Total","default":0},"page":{"type":"integer","title":"Page","default":1},"page_size":{"type":"integer","title":"Page Size","default":25}},"type":"object","title":"SubscriberListResponse","description":"``GET /{newsletter_id}/subscribers`` — preserves the internal\n``{items, total, page, page_size}`` shape verbatim."},"SubscriberSummary":{"properties":{"id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Id"},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"verification_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Verification Status"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"}},"additionalProperties":true,"type":"object","title":"SubscriberSummary","description":"A single newsletter subscriber row."},"SubtaskCreateRequest":{"properties":{"tags":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":20},{"type":"null"}],"title":"Tags","description":"Labels (max 20)."},"entity_type":{"type":"string","title":"Entity Type","description":"Record type: contact | company | deal."},"entity_id":{"type":"string","title":"Entity Id","description":"Record id."},"title":{"type":"string","title":"Title","description":"Subtask title."},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Free-text body."},"due_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Due Date","description":"ISO 8601 due date."},"assignee_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Assignee Id","description":"Assignee id."},"assignee_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Assignee Name","description":"Assignee display name."},"priority":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Priority","description":"Priority."},"task_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Task Type","description":"Task type."},"reminder_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reminder At","description":"ISO 8601 UTC reminder time. Omit for no reminder."},"visibility":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Visibility","description":"public | team | private. Omit for the org default."},"records":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Records","description":"Additional `{entity_type, entity_id}` records to link. When set, the FIRST entry becomes the primary record."},"source_url":{"anyOf":[{"type":"string","maxLength":2048},{"type":"null"}],"title":"Source Url","description":"Page the subtask was raised from."},"parent_task_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Parent Task Id","description":"Ignored - the parent is the task in the path. Present for parity."},"subtask_sort_order":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Subtask Sort Order","description":"Position among sibling subtasks."}},"type":"object","required":["entity_type","entity_id","title"],"title":"SubtaskCreateRequest","description":"Create a subtask under an existing task.\n\n`entity_type`/`entity_id` are the record the subtask hangs off, and they\nare required by the app's own model - a subtask is not implicitly attached\nto its parent's record."},"SubtaskUpdateRequest":{"properties":{"tags":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":20},{"type":"null"}],"title":"Tags","description":"Replace the labels."},"expected_updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Expected Updated At","description":"Optimistic-concurrency guard. When set and the stored row is newer, the update is refused instead of overwriting."},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title","description":"New title."},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"New body."},"due_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Due Date","description":"ISO 8601. Send explicit null to clear."},"assignee_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Assignee Id","description":"Send explicit null to unassign."},"assignee_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Assignee Name","description":"Assignee display name."},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"New status."},"priority":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Priority","description":"New priority."},"task_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Task Type","description":"Send explicit null to clear."},"reminder_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reminder At","description":"ISO 8601 UTC reminder."},"clear_reminder":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Clear Reminder","description":"Explicitly remove the reminder."},"visibility":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Visibility","description":"public | team | private."},"records":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Records","description":"Replace record links. Empty list clears them; omit to leave alone."}},"type":"object","title":"SubtaskUpdateRequest","description":"Patch a subtask. Omitted fields are left alone.\n\n`records` is the exception: an EMPTY list clears every record link, while\nomitting it leaves the links unchanged."},"SugarCrmConnectRequest":{"properties":{"instance_url":{"type":"string","title":"Instance Url","description":"Your SugarCRM instance, e.g. https://acme.sugarondemand.com."},"username":{"type":"string","title":"Username"},"password":{"type":"string","title":"Password"},"client_id":{"type":"string","title":"Client Id","description":"OAuth client id configured in SugarCRM.","default":"sugar"},"client_secret":{"type":"string","title":"Client Secret","description":"OAuth client secret, if your client id has one.","default":""}},"type":"object","required":["instance_url","username","password"],"title":"SugarCrmConnectRequest","description":"SugarCRM credentials for the password-grant connection.\n\nWRITE-ONLY: the username, password and client secret are stored encrypted\nand no operation returns them."},"SuggestCampaignsRequest":{"properties":{"organization_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Organization Id","description":"Ignored. The organisation is the API key's own."},"website_url":{"type":"string","title":"Website Url"},"campaign_goal":{"type":"string","title":"Campaign Goal"},"target_persona":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Persona"},"campaign_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Type","default":"all"}},"type":"object","required":["website_url","campaign_goal"],"title":"SuggestCampaignsRequest","description":"Generate campaign ideas from a goal. SPENDS CREDIT."},"SuggestMappingsRequest":{"properties":{"source_columns":{"items":{"type":"string"},"type":"array","maxItems":100,"minItems":1,"title":"Source Columns"},"target_fields":{"items":{"type":"string"},"type":"array","maxItems":100,"minItems":1,"title":"Target Fields"}},"type":"object","required":["source_columns","target_fields"],"title":"SuggestMappingsRequest","description":"Ask the model to map source columns onto target fields."},"SuggestRequest":{"properties":{"target":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target"},"motion_hint":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Motion Hint"},"use_brief_only":{"type":"boolean","title":"Use Brief Only","default":true}},"type":"object","title":"SuggestRequest"},"SummaryDTO":{"properties":{"survey_id":{"type":"string","title":"Survey Id"},"type":{"type":"string","title":"Type"},"delivery_channel":{"type":"string","title":"Delivery Channel"},"nps_score":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Nps Score"},"csat_avg":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Csat Avg"},"promoters":{"type":"integer","title":"Promoters"},"passives":{"type":"integer","title":"Passives"},"detractors":{"type":"integer","title":"Detractors"},"satisfied":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Satisfied"},"neutral":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Neutral"},"dissatisfied":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Dissatisfied"},"total_respondents":{"type":"integer","title":"Total Respondents"},"response_rate":{"$ref":"#/components/schemas/ResponseRateDTO"},"bucket":{"type":"string","title":"Bucket"},"time_series":{"items":{"$ref":"#/components/schemas/TrendBarDTO"},"type":"array","title":"Time Series"}},"type":"object","required":["survey_id","type","delivery_channel","promoters","passives","detractors","total_respondents","response_rate","bucket","time_series"],"title":"SummaryDTO"},"SuppressActionResponse":{"properties":{"contact_id":{"type":"integer","title":"Contact Id"},"is_suppressed":{"type":"boolean","title":"Is Suppressed"},"revision":{"type":"integer","title":"Revision"}},"type":"object","required":["contact_id","is_suppressed","revision"],"title":"SuppressActionResponse"},"SuppressContactRequest":{"properties":{"reason":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Reason"}},"type":"object","title":"SuppressContactRequest"},"SuppressionRecord":{"properties":{"id":{"type":"string","title":"Id"},"contact_id":{"type":"integer","title":"Contact Id"},"channel":{"type":"string","title":"Channel","description":"all | email | phone | linkedin"},"category":{"type":"string","title":"Category","description":"contact_initiated | org_initiated | system"},"source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source"},"source_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Ref"},"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason"},"created_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created By"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"revision":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Revision"}},"type":"object","required":["id","contact_id","channel","category"],"title":"SuppressionRecord","description":"One row of the central ``contact_suppressions`` ledger."},"SuppressionSettingsRequest":{"properties":{"contact_optout_scope":{"type":"string","enum":["channel","all"],"title":"Contact Optout Scope","description":"`channel`: an opt-out stays on its channel. `all`: it covers all outreach."}},"type":"object","required":["contact_optout_scope"],"title":"SuppressionSettingsRequest"},"SuppressionStatusResponse":{"properties":{"contact_id":{"type":"integer","title":"Contact Id"},"is_suppressed":{"type":"boolean","title":"Is Suppressed"},"active_channels":{"items":{"type":"string"},"type":"array","title":"Active Channels"},"suppressions":{"items":{"$ref":"#/components/schemas/SuppressionRecord"},"type":"array","title":"Suppressions"}},"type":"object","required":["contact_id","is_suppressed"],"title":"SuppressionStatusResponse","description":"Answer to \"is this contact suppressed, and on which channels?\"."},"SuppressionsBulkAddRequest":{"properties":{"contact_ids":{"items":{"type":"integer"},"type":"array","maxItems":5000,"minItems":1,"title":"Contact Ids"},"channel":{"type":"string","enum":["all","email","phone","linkedin"],"title":"Channel","default":"all"},"reason":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Reason"}},"type":"object","required":["contact_ids"],"title":"SuppressionsBulkAddRequest"},"SuppressionsReinstateRequest":{"properties":{"contact_ids":{"items":{"type":"integer"},"type":"array","maxItems":5000,"minItems":1,"title":"Contact Ids"},"reason":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Reason"}},"type":"object","required":["contact_ids"],"title":"SuppressionsReinstateRequest"},"SurveyDeleteResponse":{"properties":{"deleted":{"type":"boolean","title":"Deleted"},"survey_id":{"type":"string","title":"Survey Id"}},"type":"object","required":["deleted","survey_id"],"title":"SurveyDeleteResponse"},"SurveyDomainPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"SurveyDomainPayload","description":"An open envelope for a verification result.\n\nOpen because the DNS record set grows: DMARC was added to it after SPF and\nDKIM, and closing the shape would have silently dropped the record that\ndecides whether Gmail accepts the mail at all."},"SurveyResponseDTO":{"properties":{"id":{"type":"string","title":"Id"},"name":{"type":"string","title":"Name"},"type":{"type":"string","title":"Type"},"question_text":{"type":"string","title":"Question Text"},"scale_min":{"type":"integer","title":"Scale Min"},"scale_max":{"type":"integer","title":"Scale Max"},"thank_you_copy":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Thank You Copy"},"template_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Template Id"},"delivery_channel":{"type":"string","title":"Delivery Channel"},"score_field_column_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Score Field Column Id"},"comment_mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Comment Mode"},"is_active":{"type":"boolean","title":"Is Active"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"}},"type":"object","required":["id","name","type","question_text","scale_min","scale_max","delivery_channel","is_active"],"title":"SurveyResponseDTO"},"SurveyResponseRowDTO":{"properties":{"contact_id":{"type":"integer","title":"Contact Id"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name"},"score":{"type":"integer","title":"Score"},"classification":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Classification"},"channel":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Channel"},"responded_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Responded At"},"comment":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Comment"},"history":{"items":{"$ref":"#/components/schemas/SurveyScorePointDTO"},"type":"array","title":"History","default":[]},"trend":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Trend"},"response_count":{"type":"integer","title":"Response Count","default":1}},"type":"object","required":["contact_id","score"],"title":"SurveyResponseRowDTO"},"SurveyResponsesDTO":{"properties":{"survey_id":{"type":"string","title":"Survey Id"},"responses":{"items":{"$ref":"#/components/schemas/SurveyResponseRowDTO"},"type":"array","title":"Responses"}},"type":"object","required":["survey_id","responses"],"title":"SurveyResponsesDTO"},"SurveyScorePointDTO":{"properties":{"score":{"type":"integer","title":"Score"},"responded_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Responded At"},"send_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Send Id"}},"type":"object","required":["score"],"title":"SurveyScorePointDTO"},"SurveySendAccepted":{"properties":{"send_id":{"type":"integer","title":"Send Id","description":"Poll GET /surveys/sends/{send_id} for progress."},"status":{"type":"string","title":"Status","description":"Dispatch state, e.g. queued or scheduled."},"recipient_count":{"type":"integer","title":"Recipient Count","description":"Contacts resolved from the audience at accept time."}},"type":"object","required":["send_id","status","recipient_count"],"title":"SurveySendAccepted","description":"A send that has been accepted for dispatch, not yet delivered."},"SurveySendDTO":{"properties":{"id":{"type":"integer","title":"Id"},"survey_id":{"type":"string","title":"Survey Id"},"audience_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience Ref"},"channel":{"type":"string","title":"Channel"},"status":{"type":"string","title":"Status"},"recipient_count":{"type":"integer","title":"Recipient Count"},"scheduled_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Scheduled At"}},"type":"object","required":["id","survey_id","channel","status","recipient_count"],"title":"SurveySendDTO"},"SurveySendRowDTO":{"properties":{"id":{"type":"integer","title":"Id"},"channel":{"type":"string","title":"Channel"},"trigger_kind":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Trigger Kind"},"status":{"type":"string","title":"Status"},"audience_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience Ref"},"audience_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience Name"},"scheduled_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Scheduled At"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"recipient_count":{"type":"integer","title":"Recipient Count","default":0},"delivery_breakdown":{"$ref":"#/components/schemas/SendDeliveryBreakdownDTO"},"responded_count":{"type":"integer","title":"Responded Count","default":0}},"type":"object","required":["id","channel","status","delivery_breakdown"],"title":"SurveySendRowDTO"},"SurveySendingDomainDTO":{"properties":{"id":{"type":"integer","title":"Id"},"domain":{"type":"string","title":"Domain"},"status":{"type":"string","enum":["verified","pending","not_set_up"],"title":"Status"}},"type":"object","required":["id","domain","status"],"title":"SurveySendingDomainDTO"},"SurveySendsDTO":{"properties":{"survey_id":{"type":"string","title":"Survey Id"},"sends":{"items":{"$ref":"#/components/schemas/SurveySendRowDTO"},"type":"array","title":"Sends"}},"type":"object","required":["survey_id","sends"],"title":"SurveySendsDTO"},"SurveyTriggerDTO":{"properties":{"id":{"type":"string","title":"Id"},"survey_id":{"type":"string","title":"Survey Id"},"trigger_kind":{"type":"string","title":"Trigger Kind"},"audience_ref":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience Ref"},"stage_value":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stage Value"},"cadence_days":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Cadence Days"},"sender_email":{"type":"string","title":"Sender Email"},"subject":{"type":"string","title":"Subject"},"sender_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sender Name"},"reply_to":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reply To"},"is_active":{"type":"boolean","title":"Is Active"}},"type":"object","required":["id","survey_id","trigger_kind","sender_email","subject","is_active"],"title":"SurveyTriggerDTO"},"SurveyTriggerDeleteResponse":{"properties":{"deleted":{"type":"boolean","title":"Deleted"},"trigger_id":{"type":"string","title":"Trigger Id"},"survey_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Survey Id"}},"type":"object","required":["deleted","trigger_id"],"title":"SurveyTriggerDeleteResponse"},"SyncEnabledRequest":{"properties":{"connection_id":{"type":"string","title":"Connection Id","description":"Which CRM connection."},"enabled":{"type":"boolean","title":"Enabled","description":"Explicit, not a toggle - a retried request is then idempotent."}},"type":"object","required":["connection_id","enabled"],"title":"SyncEnabledRequest","description":"Turn continuous sync on or off for one connection."},"SyncErrorResponse":{"properties":{"id":{"type":"integer","title":"Id"},"started_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Started At"},"error_message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Error Message"},"details":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Details"}},"type":"object","required":["id"],"title":"SyncErrorResponse"},"SyncJobResponse":{"properties":{"job_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Id"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"}},"additionalProperties":true,"type":"object","title":"SyncJobResponse","description":"A bulk job, or its status. Open-shaped - the payload carries per-provider\nprogress detail that differs between CRMs and grows with them."},"SyncRunResponse":{"properties":{"id":{"type":"integer","title":"Id"},"started_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Started At"},"finished_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Finished At"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"members_added":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Members Added"},"members_removed":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Members Removed"},"total_members":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Total Members"},"error_message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Error Message"}},"type":"object","required":["id"],"title":"SyncRunResponse"},"SyncSchedule":{"properties":{"frequency":{"type":"string","enum":["manual","hourly","daily","weekly"],"title":"Frequency","default":"daily"},"timezone":{"type":"string","title":"Timezone","default":"UTC"},"time":{"type":"string","pattern":"^(?:[01][0-9]|2[0-3]):[0-5][0-9]$","title":"Time","default":"02:00"},"weekdays":{"items":{"type":"integer"},"type":"array","maxItems":7,"minItems":1,"title":"Weekdays"}},"additionalProperties":false,"type":"object","title":"SyncSchedule","description":"When the reconciliation runs."},"TableConnectionRequest":{"properties":{"destination_table_id":{"type":"string","format":"uuid","title":"Destination Table Id"},"sync_mode":{"type":"string","const":"append","title":"Sync Mode","default":"append"},"field_mapping":{"anyOf":[{"additionalProperties":{"type":"string"},"type":"object"},{"type":"null"}],"title":"Field Mapping","description":"Source column -> destination."},"filter_conditions":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Filter Conditions"}},"type":"object","required":["destination_table_id"],"title":"TableConnectionRequest","description":"Copy rows from this table into another table in the same organisation."},"TagCreateRequest":{"properties":{"name":{"type":"string","minLength":1,"title":"Name","description":"Tag name, unique per organisation."},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"color":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Color"},"priority":{"anyOf":[{"type":"integer","maximum":100.0,"minimum":1.0},{"type":"null"}],"title":"Priority","description":"1-100."},"rules":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Rules","description":"Plain-language rules the auto-tagger applies this tag by."},"agent_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent Id","description":"AI Inbox agent that answers threads carrying this tag."},"ai_can_apply":{"type":"boolean","title":"Ai Can Apply","description":"Whether the auto-tagger may apply this tag on its own.","default":false}},"type":"object","required":["name"],"title":"TagCreateRequest","description":"Create an inbox tag. Mirrors `ai_inbox.schemas.tags.TagCreateRequest`."},"TagUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"color":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Color"},"priority":{"anyOf":[{"type":"integer","maximum":100.0,"minimum":1.0},{"type":"null"}],"title":"Priority","description":"1-100."},"rules":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Rules","description":"Natural-language rules the AI uses to decide the tag applies."},"agent_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent Id"},"ai_can_apply":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Ai Can Apply","description":"Whether the AI may apply this tag on its own."}},"type":"object","title":"TagUpdateRequest","description":"Edit an inbox tag.\n\nEvery field is optional, but the app writes the model as given, so send the\nwhole tag rather than only the field you are changing."},"TailorQueryParamSetRequest":{"properties":{"name":{"type":"string","maxLength":255,"minLength":3,"title":"Name"},"settings":{"additionalProperties":true,"type":"object","title":"Settings","description":"The saved parameter selection."}},"type":"object","required":["name"],"title":"TailorQueryParamSetRequest","description":"A named, saved set of page-personalisation query parameters."},"TalentProfileUpdateRequest":{"properties":{"first_name":{"anyOf":[{"type":"string","maxLength":100,"minLength":1},{"type":"null"}],"title":"First Name"},"last_name":{"anyOf":[{"type":"string","maxLength":100,"minLength":1},{"type":"null"}],"title":"Last Name"},"country_code":{"anyOf":[{"type":"string","maxLength":2,"minLength":2},{"type":"null"}],"title":"Country Code"},"marketplace_role":{"anyOf":[{"type":"string","enum":["sdr","ae","gtm_engineer","campaign_manager"]},{"type":"null"}],"title":"Marketplace Role"},"phone":{"anyOf":[{"type":"string","maxLength":30},{"type":"null"}],"title":"Phone"},"monthly_rate_usd":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Monthly Rate Usd"},"per_meeting_rate_usd":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Per Meeting Rate Usd"},"availability_status":{"anyOf":[{"type":"string","enum":["open","limited","fully_booked","hidden"]},{"type":"null"}],"title":"Availability Status"},"bio":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bio"},"tagline":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Tagline"},"summary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Summary"},"linkedin_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Linkedin Url"},"video_intro_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Video Intro Url"},"skills":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Skills"},"work_experience":{"anyOf":[{"items":{},"type":"array"},{"type":"null"}],"title":"Work Experience"},"industries_worked":{"anyOf":[{"items":{},"type":"array"},{"type":"null"}],"title":"Industries Worked"},"tools_experience":{"anyOf":[{"items":{},"type":"array"},{"type":"null"}],"title":"Tools Experience"},"is_anonymous":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Anonymous","description":"Incognito. Buyers see a stable codename until they hire you; the reveal is permanent."}},"type":"object","title":"TalentProfileUpdateRequest","description":"Partial edit of the caller's own marketplace profile.\n\nEvery field is optional so a wizard can PATCH one step at a time. Changing\n`country_code` RECOMPUTES the payout track and cascades to the connect and\npayout-account rows - an unsupported country is refused with a 400 rather\nthan silently landing on a rail that cannot pay it.\n\nAn agency-managed rep may not edit `monthly_rate_usd` /\n`per_meeting_rate_usd`: the agency sets the client-facing price and the rep\nis not permitted to see or change it (403)."},"TamGenerateRequest":{"properties":{"website_url":{"type":"string","title":"Website Url","description":"The website the TAM is defined for."}},"type":"object","required":["website_url"],"title":"TamGenerateRequest"},"TamUpdateRequest":{"properties":{"website_url":{"type":"string","title":"Website Url","description":"The website whose TAM definition is edited."},"definition":{"additionalProperties":true,"type":"object","title":"Definition","description":"The full TAM definition to store."},"change_summary":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Change Summary","description":"A note recorded with the new version."}},"type":"object","required":["website_url","definition"],"title":"TamUpdateRequest"},"TaskAssignmentRequest":{"properties":{"agent_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Agent Id"},"expected_updated_at":{"type":"string","format":"date-time","title":"Expected Updated At"}},"additionalProperties":false,"type":"object","required":["expected_updated_at"],"title":"TaskAssignmentRequest"},"TaskAssignmentResult":{"properties":{"assigned":{"type":"boolean","title":"Assigned"},"execution_started":{"type":"boolean","title":"Execution Started"}},"type":"object","required":["assigned","execution_started"],"title":"TaskAssignmentResult"},"TaskCompletionSettingsRequest":{"properties":{"parent_completion_mode":{"anyOf":[{"type":"string","enum":["manual","auto_complete","require_subtasks_done"]},{"type":"null"}],"title":"Parent Completion Mode","description":"How a parent task completes relative to its subtasks."}},"type":"object","title":"TaskCompletionSettingsRequest","description":"Mirrors `UpdateTaskSettingsRequest`. The app accepts exactly these three modes."},"TaskCopyRequest":{"properties":{"request_id":{"type":"string","format":"uuid","title":"Request Id"},"expected_updated_at":{"type":"string","format":"date-time","title":"Expected Updated At"},"assignee_ids":{"items":{"type":"string","format":"uuid"},"type":"array","maxItems":20,"minItems":1,"title":"Assignee Ids"}},"additionalProperties":false,"type":"object","required":["request_id","expected_updated_at","assignee_ids"],"title":"TaskCopyRequest"},"TaskCreateRequest":{"properties":{"tags":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":20},{"type":"null"}],"title":"Tags"},"task_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Task Type","description":"Activity type, such as call or meeting"},"entity_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Type"},"entity_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Id"},"records":{"anyOf":[{"items":{"additionalProperties":{"type":"string"},"type":"object"},"type":"array"},{"type":"null"}],"title":"Records","description":"Optional related records: contact, company, deal, lead, application, team_member, or campaign (Studio). An empty list leaves the task standalone."},"source_url":{"anyOf":[{"type":"string","maxLength":2048},{"type":"null"}],"title":"Source Url"},"title":{"type":"string","title":"Title","description":"Task title"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Task description"},"due_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Due Date","description":"Due date (ISO 8601)"},"assignee_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Assignee Id","description":"User ID to assign the task to"},"priority":{"anyOf":[{"type":"integer","maximum":4.0,"minimum":0.0},{"type":"null"}],"title":"Priority","description":"Priority (0=none, 1=high, 2=medium, 3=low; historical 4=low is preserved)"},"parent_task_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Parent Task Id","description":"Parent task UUID. When set, this task is inserted as a subtask of the parent. Subtasks cannot themselves have subtasks (one level deep)."},"subtask_sort_order":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Subtask Sort Order","description":"Sort position within the parent's subtasks. When omitted on a subtask create, the handler appends to the end."}},"type":"object","required":["title"],"title":"TaskCreateRequest"},"TaskExecutionHistory":{"properties":{"runs":{"items":{"$ref":"#/components/schemas/TaskExecutionRun"},"type":"array","title":"Runs"}},"type":"object","required":["runs"],"title":"TaskExecutionHistory"},"TaskExecutionRun":{"properties":{"work_item_id":{"type":"string","format":"uuid","title":"Work Item Id"},"status":{"type":"string","title":"Status"},"continued_after_reply":{"type":"boolean","title":"Continued After Reply","default":false},"details_available":{"type":"boolean","title":"Details Available"},"current_step":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Current Step"},"next_action":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Next Action"},"created_at":{"type":"string","format":"date-time","title":"Created At"},"completed_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Completed At"},"session_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Session Id"}},"type":"object","required":["work_item_id","status","details_available","current_step","next_action","created_at","completed_at","session_id"],"title":"TaskExecutionRun"},"TaskReplyCreateRequest":{"properties":{"body":{"type":"string","title":"Body","description":"Reply text."},"author_avatar_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Author Avatar Url","description":"Avatar to show beside the reply."},"mentioned_user_ids":{"items":{"type":"string"},"type":"array","title":"Mentioned User Ids","description":"Users to notify."}},"type":"object","required":["body"],"title":"TaskReplyCreateRequest","description":"Post a reply on a task's discussion thread. Internal to the org."},"TaskReplyUpdateRequest":{"properties":{"body":{"type":"string","title":"Body","description":"Replacement text."}},"type":"object","required":["body"],"title":"TaskReplyUpdateRequest","description":"Edit a reply. Author only."},"TaskResponse":{"properties":{"tags":{"items":{"type":"string"},"type":"array","title":"Tags"},"executor_type":{"type":"string","enum":["human","agent"],"title":"Executor Type","default":"human"},"executor_agent_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Executor Agent Id"},"executor_agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Executor Agent Name"},"execution_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Execution Id"},"entity_label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Label"},"links":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Links"},"source_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Url"},"source_external_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source External Id"},"source_meeting_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Source Meeting Id"},"source_transcript_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Transcript Id"},"source_meeting_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Meeting Title"},"source_meeting_start_time":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Meeting Start Time"},"visibility":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Visibility"},"reminder_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reminder At"},"reminder_sent_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reminder Sent At"},"id":{"type":"string","title":"Id"},"entity_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Type"},"entity_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Id"},"title":{"type":"string","title":"Title"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"due_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Due Date"},"assignee_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Assignee Id"},"assignee_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Assignee Name"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"priority":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Priority"},"task_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Task Type"},"created_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created By"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"},"parent_task_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Parent Task Id"},"subtask_sort_order":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Subtask Sort Order"},"subtask_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Subtask Count"},"completed_subtask_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Completed Subtask Count"}},"type":"object","required":["id","title"],"title":"TaskResponse"},"TaskSettingsUpdateRequest":{"properties":{"default_visibility":{"anyOf":[{"type":"string","enum":["public","team","private"]},{"type":"null"}],"title":"Default Visibility","description":"Default visibility for newly created tasks."},"notes_anywhere_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Notes Anywhere Enabled","description":"When false, hide the global Quick Note shortcut and its command-palette action."},"selection_toolbar_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Selection Toolbar Enabled","description":"When false, hide the floating 'Add note' bubble on text selection."},"mentions_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Mentions Enabled","description":"When false, hide @ autocomplete in note and reply composers."},"notify_on_mention":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Notify On Mention","description":"When false, suppress mention-triggered bell notifications."},"parent_completion_mode":{"anyOf":[{"type":"string","enum":["manual","auto_complete","require_subtasks_done"]},{"type":"null"}],"title":"Parent Completion Mode","description":"How a parent task completes relative to its subtasks."}},"type":"object","title":"TaskSettingsUpdateRequest","description":"Mirrors `UpdateTaskSettingsRequest`. Partial update, but not an EMPTY one.\n\nThe app refuses a patch that sets nothing (422) rather than no-opping, and\nthat refusal is worth keeping: an empty body is always a caller bug, and a\nsilent 200 hides it.\n\n`default_visibility` and `parent_completion_mode` are Literals here where\nthe app takes `str` and rejects an unknown value from inside the handler.\nSame outcome, one layer earlier, and the legal values are in the schema."},"TaskStartResult":{"properties":{"work_item_id":{"type":"string","format":"uuid","title":"Work Item Id"},"workflow_started":{"type":"boolean","title":"Workflow Started"},"session_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Session Id"},"already_started":{"type":"boolean","title":"Already Started","default":false},"message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Message"}},"type":"object","required":["work_item_id","workflow_started"],"title":"TaskStartResult"},"TaskUpdateRequest":{"properties":{"tags":{"anyOf":[{"items":{"type":"string"},"type":"array","maxItems":20},{"type":"null"}],"title":"Tags"},"expected_updated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Expected Updated At"},"task_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Task Type","description":"Activity type; null removes the saved type"},"records":{"anyOf":[{"items":{"additionalProperties":{"type":"string"},"type":"object"},"type":"array"},{"type":"null"}],"title":"Records","description":"Replace related records; an empty list removes all links and makes the task standalone. Omit to preserve existing links."},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title","description":"Task title"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Task description"},"due_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Due Date","description":"Due date (ISO 8601)"},"assignee_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Assignee Id","description":"User ID to assign the task to"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"Task status (open, completed)"},"priority":{"anyOf":[{"type":"integer","maximum":4.0,"minimum":0.0},{"type":"null"}],"title":"Priority","description":"Priority (0=none, 1=high, 2=medium, 3=low; historical 4=low is preserved)"},"parent_task_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Parent Task Id","description":"New parent task UUID. Re-parents this task into a subtask of the given parent. Parent must exist and must not itself be a subtask."},"subtask_sort_order":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Subtask Sort Order","description":"New sort position within the parent's subtasks (reorder)."}},"type":"object","title":"TaskUpdateRequest"},"TeamConfigUpdateRequest":{"properties":{"visible_columns":{"anyOf":[{"additionalProperties":{"items":{"type":"string"},"type":"array"},"type":"object"},{"type":"null"}],"title":"Visible Columns"},"visible_periods":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Visible Periods"},"default_period":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Default Period"},"goals":{"anyOf":[{"additionalProperties":{"additionalProperties":true,"type":"object"},"type":"object"},{"type":"null"}],"title":"Goals"},"tv_rotation_seconds":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Tv Rotation Seconds"},"team_command_center_enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Team Command Center Enabled"}},"additionalProperties":true,"type":"object","title":"TeamConfigUpdateRequest","description":"Team Command Center settings.\n\nOPEN (`extra=\"allow\"`), mirroring the app's `TeamFloorConfigUpdate`, which\ncarries the same and says in its own docstring that it is an INTENTIONAL\ndeviation from the `extra=\"forbid\"` rule its sibling JSONB endpoints\nfollow. Closing it here would reject a key the app itself stores.\n\nEvery field is optional; only what you send is written."},"TeamCreateRequest":{"properties":{"name":{"type":"string","maxLength":100,"minLength":1,"title":"Name"},"type":{"type":"string","maxLength":50,"title":"Type","default":"functional"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"color":{"anyOf":[{"type":"string","maxLength":20,"pattern":"^(#[0-9A-Fa-f]{6})?$"},{"type":"null"}],"title":"Color","description":"Hex colour, e.g. #FF5733. An empty string clears it."},"agent_id":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Agent Id"},"chat_intent":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Chat Intent","description":"'support' | 'sales' | null"},"members":{"anyOf":[{"items":{"$ref":"#/components/schemas/WorkspaceMemberInput"},"type":"array"},{"type":"null"}],"title":"Members"},"mailbox_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Mailbox Ids"},"phone_number_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Phone Number Ids"},"linkedin_account_ids":{"anyOf":[{"items":{"type":"string","format":"uuid"},"type":"array"},{"type":"null"}],"title":"Linkedin Account Ids"},"campaign_ids":{"anyOf":[{"items":{"type":"string","format":"uuid"},"type":"array"},{"type":"null"}],"title":"Campaign Ids"},"sequence_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Sequence Ids"},"chatbot_ids":{"anyOf":[{"items":{"type":"string","format":"uuid"},"type":"array"},{"type":"null"}],"title":"Chatbot Ids"}},"type":"object","required":["name"],"title":"TeamCreateRequest","description":"Create a team. Mirrors `teams.TeamCreateDTO`.\n\nEvery `*_ids` list is applied in the SAME transaction as the team row, so\na team is never briefly visible with none of its channels attached."},"TeamListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"TeamListPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape."},"TeamMemberAddRequest":{"properties":{"user_id":{"type":"string","maxLength":255,"minLength":1,"title":"User Id"},"team_role":{"type":"string","maxLength":20,"title":"Team Role","default":"member"}},"type":"object","required":["user_id"],"title":"TeamMemberAddRequest","description":"Put a person (or an agent) on a team. Mirrors `teams.TeamMemberAddDTO`."},"TeamMemberRoleUpdateRequest":{"properties":{"team_role":{"type":"string","maxLength":20,"title":"Team Role"}},"type":"object","required":["team_role"],"title":"TeamMemberRoleUpdateRequest","description":"Change someone's role WITHIN a team. Mirrors `teams.TeamMemberUpdateDTO`."},"TeamPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"TeamPayload","description":"An open envelope for a config, a bootstrap or a data response.\n\nOpen because the leaderboard and set DATA responses carry one key per KPI\nand the KPI catalogue is org-configurable: a closed model would drop a\ncustomer's own metric, and a leaderboard missing a column reads as a rep\nhaving scored nothing."},"TeamUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":100,"minLength":1},{"type":"null"}],"title":"Name"},"type":{"anyOf":[{"type":"string","maxLength":50},{"type":"null"}],"title":"Type"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"color":{"anyOf":[{"type":"string","maxLength":20,"pattern":"^(#[0-9A-Fa-f]{6})?$"},{"type":"null"}],"title":"Color","description":"Hex colour, e.g. #FF5733. An empty string clears it."},"agent_id":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Agent Id","description":"Single workspace AI agent; empty string clears it."},"chat_intent":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Chat Intent","description":"'support' | 'sales' | null. An empty string clears it."},"members":{"anyOf":[{"items":{"$ref":"#/components/schemas/WorkspaceMemberInput"},"type":"array"},{"type":"null"}],"title":"Members"},"mailbox_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Mailbox Ids"},"phone_number_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Phone Number Ids"},"linkedin_account_ids":{"anyOf":[{"items":{"type":"string","format":"uuid"},"type":"array"},{"type":"null"}],"title":"Linkedin Account Ids"},"campaign_ids":{"anyOf":[{"items":{"type":"string","format":"uuid"},"type":"array"},{"type":"null"}],"title":"Campaign Ids"},"sequence_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Sequence Ids"},"chatbot_ids":{"anyOf":[{"items":{"type":"string","format":"uuid"},"type":"array"},{"type":"null"}],"title":"Chatbot Ids"}},"type":"object","title":"TeamUpdateRequest","description":"Update a team. Mirrors `teams.TeamUpdateDTO`.\n\nAn omitted `*_ids` list LEAVES that attachment alone; a list that is\npresent REPLACES it (the handler diffs). Sending `[]` therefore detaches\neverything of that kind, which is not the same instruction as omitting it."},"TemplateCloneRequest":{"properties":{"source":{"type":"string","title":"Source","description":"`url`, `past_issue` or `html`."},"url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Url"},"issue_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Issue Id"},"html":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Html"},"reskin":{"type":"boolean","title":"Reskin","description":"Restyle the import to the org's brand.","default":true},"keep_images":{"type":"boolean","title":"Keep Images","description":"Keep the original images rather than dropping them.","default":false}},"type":"object","required":["source"],"title":"TemplateCloneRequest","description":"Import an existing email as a template.\n\n`source` says which of the three optional inputs is the real one: `url`\nreads `url`, `past_issue` reads `issue_id`, `html` reads `html`. It is\ndeliberately left an open string rather than a `Literal`, because the app\nleaves it open - closing it here would 422 a source the app added."},"TemplateFromLayoutRequest":{"properties":{"archetype_key":{"type":"string","title":"Archetype Key","description":"Which layout to build from."},"audience_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience Id","description":"Audience the copy is aimed at."}},"type":"object","required":["archetype_key"],"title":"TemplateFromLayoutRequest","description":"Build a template from a named layout archetype. ASYNC and AI-backed."},"TemplateFromPromptRequest":{"properties":{"idea":{"type":"string","title":"Idea","description":"What the email should say, in plain words."},"goal":{"type":"string","title":"Goal","description":"What it is for, e.g. `product`.","default":"product"},"audience_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience Id"},"tone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Tone"},"length":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Length"},"voice_reference_issue_ids":{"items":{"type":"string"},"type":"array","title":"Voice Reference Issue Ids","description":"Past issues to imitate the voice of."},"variants":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Variants","description":"How many alternatives to generate.","default":1}},"type":"object","required":["idea"],"title":"TemplateFromPromptRequest","description":"Build a template from a plain-language idea. ASYNC and AI-backed."},"TemplateGenerationStatusBatchRequest":{"properties":{"template_ids":{"items":{"type":"integer"},"type":"array","maxItems":200,"title":"Template Ids"}},"type":"object","required":["template_ids"],"title":"TemplateGenerationStatusBatchRequest","description":"Poll many template builds in one call.\n\nCapped at 200 ids, matching the app. The cap is not arbitrary: a dashboard\npolls this every two seconds and an unbounded `IN (...)` is a denial-of-\nservice surface, which is why it is enforced here as a 422 rather than\nreached inside the handler."},"ToggleAutoEnrichRequest":{"properties":{"enabled":{"type":"boolean","title":"Enabled"},"batch_size":{"type":"integer","maximum":1000.0,"minimum":1.0,"title":"Batch Size","description":"Rows per automatic batch.","default":10}},"type":"object","required":["enabled"],"title":"ToggleAutoEnrichRequest","description":"Turn the table's automatic AI enrichment on or off.\n\n`enabled` is explicit rather than a toggle, so a retried request is\nidempotent instead of flipping the state back - which on this switch would\nsilently resume spending."},"ToggleWorkflowRequest":{"properties":{"active":{"type":"boolean","title":"Active"}},"type":"object","required":["active"],"title":"ToggleWorkflowRequest"},"TokenResponse":{"properties":{"access_token":{"type":"string","title":"Access Token","description":"The signed app JWT"},"token_type":{"type":"string","title":"Token Type","description":"Always 'Bearer'","default":"Bearer"},"expires_in":{"type":"integer","title":"Expires In","description":"Lifetime in seconds"},"audience":{"type":"string","title":"Audience","description":"The distinct-per-app, per-environment audience"},"app_id":{"type":"string","title":"App Id","description":"App the token is bound to"},"kid":{"type":"string","title":"Kid","description":"Signing key id (matches a JWKS entry)"}},"type":"object","required":["access_token","expires_in","audience","app_id","kid"],"title":"TokenResponse","description":"The minted token + the non-secret metadata a client needs."},"TouchCandidate":{"properties":{"channel":{"type":"string","const":"rep_email","title":"Channel"},"touched_at":{"type":"string","format":"date-time","title":"Touched At"},"summary":{"anyOf":[{"type":"string","maxLength":300},{"type":"null"}],"title":"Summary"},"email":{"type":"string","title":"Email"},"ref_type":{"type":"string","const":"rfc_message_id","title":"Ref Type"},"ref_id":{"type":"string","maxLength":998,"minLength":1,"title":"Ref Id"},"initiated_by":{"anyOf":[{"type":"string","enum":["rep","prospect"]},{"type":"null"}],"title":"Initiated By"},"token":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Token","description":"Signed by `touches/search`, valid for 30 minutes."}},"type":"object","required":["channel","touched_at","email","ref_type","ref_id"],"title":"TouchCandidate","description":"One candidate exactly as `touches/search` returned it, `token` included (the token is what authorises it)."},"TrackDocumentUsageRequest":{"properties":{"usage_type":{"type":"string","enum":["creation","citation"],"title":"Usage Type","description":"`creation`: the document was used to generate new content. `citation`: the document was quoted or referenced."},"source_type":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Source Type","description":"Where the use happened, e.g. `campaign`, `account`, `copilot`, `research`. Free-form."},"source_id":{"anyOf":[{"type":"string","maxLength":128},{"type":"null"}],"title":"Source Id","description":"ID of the entity that used the document, if any."}},"type":"object","required":["usage_type"],"title":"TrackDocumentUsageRequest","description":"Mirrors the app handler's query parameters field for field."},"TrackedLinkRequest":{"properties":{"destination_url":{"type":"string","title":"Destination Url","description":"Absolute http(s) URL the link points at."},"link_name":{"type":"string","maxLength":120,"minLength":1,"title":"Link Name","description":"Display name. REQUIRED, and not cosmetic: clicks are GROUPED by it, so two links sharing a name report as one."},"params":{"additionalProperties":{"type":"string"},"type":"object","title":"Params","description":"Static custom params baked into the token."},"contact_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Contact Id","description":"Attribute every click on this link to one contact."},"shorten":{"type":"boolean","title":"Shorten","description":"Mint the LinkedIn-safe short form (`{base}/t/{token}`) for surfaces that strip fragments and query params.","default":false},"placement":{"type":"string","pattern":"^(fragment|query)$","title":"Placement","description":"Where the token goes when NOT shortened: `fragment` (`#t=...`) or `query` (`?g8t=...`). Ignored when `shorten` is true.","default":"fragment"},"stream_id":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Stream Id","description":"PUBLIC KEY id of the stream clicks are attributed to - the id shape `GET /visitors/streams/list` emits, NOT the stream object's own id. Falls back to the org's dedicated `tracked-links` stream when unset or unresolvable, and is only meaningful with `shorten=true`."}},"type":"object","required":["destination_url","link_name"],"title":"TrackedLinkRequest","description":"Mint a tracked short link."},"TranslateThreadRequest":{"properties":{"target_lang":{"type":"string","const":"en","title":"Target Lang","description":"Target ISO 639-1 language; only English for now.","default":"en"}},"type":"object","title":"TranslateThreadRequest","description":"Translate an email thread's messages."},"TrendBarDTO":{"properties":{"period":{"type":"string","title":"Period"},"nps_score":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Nps Score"},"csat_avg":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Csat Avg"},"promoters":{"type":"integer","title":"Promoters"},"passives":{"type":"integer","title":"Passives"},"detractors":{"type":"integer","title":"Detractors"},"total":{"type":"integer","title":"Total"}},"type":"object","required":["period","promoters","passives","detractors","total"],"title":"TrendBarDTO"},"TrendsDTO":{"properties":{"survey_id":{"type":"string","title":"Survey Id"},"type":{"type":"string","title":"Type"},"delivery_channel":{"type":"string","title":"Delivery Channel"},"bucket":{"type":"string","title":"Bucket"},"bars":{"items":{"$ref":"#/components/schemas/TrendBarDTO"},"type":"array","title":"Bars"}},"type":"object","required":["survey_id","type","delivery_channel","bucket","bars"],"title":"TrendsDTO"},"TwinLinkedInExtract":{"properties":{"linkedin_url":{"type":"string","minLength":1,"title":"Linkedin Url","description":"A LinkedIn profile URL, e.g. https://linkedin.com/in/name"}},"type":"object","required":["linkedin_url"],"title":"TwinLinkedInExtract","description":"`POST /api/v1/twins/extract-linkedin` binds `linkedin_url` as a FORM\nfield; this is the JSON shape the API takes and the router re-encodes."},"UniversalActivityQuery":{"properties":{"page_size":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Page Size","description":"Rows per page (1-100).","default":15},"cursor":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Cursor","description":"Opaque cursor from the previous page."},"queue":{"anyOf":[{"type":"string","enum":["hot_replies","follow_up","booked_meetings","everything"]},{"type":"null"}],"title":"Queue","description":"Named queue to read."},"channels":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Channels","description":"Restrict to channels, e.g. `[\"email\", \"sms\"]`."},"direction":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Direction","description":"`inbound` or `outbound`."},"tag_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Tag Ids"},"exclude_tag_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Exclude Tag Ids"},"campaign_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Campaign Ids"},"assignee_emails":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Assignee Emails"},"updated_after":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated After"},"updated_before":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated Before"},"contact_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contact Id"},"company_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Id"},"workspace_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Workspace Id","description":"Workspace UUID; omit for org-wide."},"workspace_all_mail":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Workspace All Mail","description":"Only meaningful with `workspace_id`. A workspace normally auto-scopes the email leg to its own campaign and direct sequences; set true to show all mail through that workspace's mailboxes."},"search":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Search"}},"type":"object","title":"UniversalActivityQuery","description":"Filter set for the unified activity timeline. Every field is optional.\n\n`org_id` is deliberately ABSENT: the org comes from the API key's own\nprincipal, never from the body, so a client cannot steer the query at\nanother tenant."},"UnlockContactInfoRequest":{"properties":{"contact_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array","maxItems":1000},{"type":"null"}],"title":"Contact Ids","description":"Contacts to unlock (max 1000)."},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id","description":"Unlock the contacts in this list."},"allMatching":{"type":"boolean","title":"Allmatching","description":"Resolve the complete matching set server-side.","default":false},"filterModel":{"additionalProperties":true,"type":"object","title":"Filtermodel","description":"Per-column filters."},"segmentFilter":{"anyOf":[{"$ref":"#/components/schemas/SegmentFilterGroup"},{"type":"null"}],"description":"Advanced AND/OR filter tree."}},"type":"object","title":"UnlockContactInfoRequest","description":"Reveal withheld contact details. SPENDS CREDITS.\n\nCharges per contact actually unlocked. Already-unlocked contacts are not\ncharged again, so re-sending the same ids is safe but not free to compute."},"UnlockStagingRowsRequest":{"properties":{"row_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array","maxItems":100000},{"type":"null"}],"title":"Row Ids","description":"Rows to act on. OMIT to mean EVERY locked row in the table."},"exclude_row_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array","maxItems":100000},{"type":"null"}],"title":"Exclude Row Ids","description":"Rows to leave locked."},"approved_max_credits":{"anyOf":[{"type":"integer","minimum":0.0},{"type":"null"}],"title":"Approved Max Credits","description":"Ceiling the caller approves. The run refuses to exceed it."},"quote_expires_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Quote Expires At","description":"Expiry of the quote being approved."},"operation_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Operation Id","description":"The quote's operation id. REQUIRED by the unlock - it is what ties the charge to a price the caller was shown, and it makes a retried unlock idempotent instead of charging twice."}},"type":"object","title":"UnlockStagingRowsRequest","description":"Which locked rows to price, or to unlock.\n\nThe SAME body serves the quote and the unlock. Send identical fields to\nboth: the quote prices exactly the scope the unlock will then charge for.\n\nOMITTING `row_ids` MEANS EVERY LOCKED ROW IN THE TABLE. That is the app's\n\"Unlock All\", and at one credit per row it is the most expensive thing this\nbody can express. `exclude_row_ids` narrows it back down."},"UnsuppressActionResponse":{"properties":{"contact_id":{"type":"integer","title":"Contact Id"},"is_suppressed":{"type":"boolean","title":"Is Suppressed"},"channels_cleared":{"items":{"type":"string"},"type":"array","title":"Channels Cleared"}},"type":"object","required":["contact_id","is_suppressed"],"title":"UnsuppressActionResponse"},"UpdateAIConfigRequest":{"properties":{"config":{"$ref":"#/components/schemas/AIEnrichmentConfigDto"}},"type":"object","required":["config"],"title":"UpdateAIConfigRequest","description":"Replace an AI enrichment group's definition."},"UpdateAdCampaignRequest":{"properties":{"action":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Action"},"name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Name"},"daily_budget":{"anyOf":[{"type":"number","exclusiveMinimum":0.0},{"type":"null"}],"title":"Daily Budget"},"end_date":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"End Date"},"headline":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Headline"},"primary_text":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Primary Text"},"cta":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Cta"},"destination_url":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Destination Url"},"creative_image_url":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Creative Image Url"},"creative_image_url_square":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Creative Image Url Square"},"creative_image_url_portrait":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Creative Image Url Portrait"},"logo_image_url":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Logo Image Url"},"auto_pause_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Auto Pause At","description":"Absolute UTC instant to auto-pause at (ISO-8601 with offset)"},"auto_pause_tz":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Auto Pause Tz"},"spend_cap":{"anyOf":[{"type":"number","exclusiveMinimum":0.0},{"type":"null"}],"title":"Spend Cap"},"clear_auto_stop":{"type":"boolean","title":"Clear Auto Stop","default":false},"keywords":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Keywords","description":"Google Search only: COMPLETE desired keyword list [{text, match_type, negative, paused, cpc_bid}]"},"rsa_headlines":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Rsa Headlines","description":"Google Search only: COMPLETE list of 3-15 RSA headlines (<=30 chars each)"},"rsa_descriptions":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Rsa Descriptions","description":"Google Search only: COMPLETE list of 2-4 RSA descriptions (<=90 chars each)"},"video_asset_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Video Asset Ids","description":"Google Video only: COMPLETE list of 1-5 ad_video_assets ids (None = unchanged)"},"video_headlines":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Video Headlines","description":"Google Video only: COMPLETE list, 3-5 × ≤40"},"video_long_headlines":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Video Long Headlines","description":"Google Video only: COMPLETE list, 3-5 × ≤90"},"video_descriptions":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Video Descriptions","description":"Google Video only: COMPLETE list, 3-5 × ≤90"},"video_business_name":{"anyOf":[{"type":"string","maxLength":25},{"type":"null"}],"title":"Video Business Name","description":"Google Video only: ≤25 chars"},"video_cta":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Video Cta","description":"Google Video only: CallToActionType value"},"selected_channels":{"anyOf":[{"additionalProperties":{"type":"boolean"},"type":"object"},{"type":"null"}],"title":"Selected Channels","description":"Google Video only: COMPLETE placement map (7 DemandGenSelectedChannels keys)"},"geo_targets":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Geo Targets","description":"Google only: COMPLETE list of geo target constant ids, e.g. [\"2840\"]"},"campaign_negative_keywords":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Campaign Negative Keywords","description":"Google only: COMPLETE desired campaign-level negative keywords [{text, match_type}]"}},"additionalProperties":false,"type":"object","title":"UpdateAdCampaignRequest","description":"Body for ``PUT /campaigns/{id}`` and ``POST /campaigns/{id}/edit-preview``.\n\n``extra=\"forbid\"`` is load-bearing (PRD hazard H8): the model used to inherit\nPydantic's default ``extra=\"ignore\"``, so the wizard could POST a field the\nbackend had never wired, get a 200, and render a green \"Campaign updated\"\ntoast for an edit that reached nothing. An unknown field is now a 422 —\na phantom control is structurally impossible to ship.\n\nList-shaped fields (``keywords``, ``rsa_headlines``, ``rsa_descriptions``,\n``geo_targets``) are COMPLETE desired lists, never deltas. Google replaces\nrepeated fields wholesale, so a partial list silently deletes the omitted\nentries; the handler read-modify-writes against the platform's current state.\n``None`` means \"not provided / unchanged\" — an empty list is a real request\nto clear, and is rejected where clearing would break the ad."},"UpdateAdCreativeRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"headline":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Headline"},"primary_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Primary Text"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"cta":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Cta"}},"type":"object","title":"UpdateAdCreativeRequest","description":"Edit the copy by hand. No model runs, nothing is spent."},"UpdateAssigneeRequest":{"properties":{"phone_number":{"type":"string","title":"Phone Number","description":"The number to reassign, E.164."},"assignee":{"type":"string","title":"Assignee","description":"Who owns it now. This drives inbound ring targeting, missed-call notification and the outbound caller-ID pool - it is not a label."}},"type":"object","required":["phone_number","assignee"],"title":"UpdateAssigneeRequest","description":"Move a number to a different person.\n\nMirrors `phone_numbers.interfaces.fastapi.dtos.UpdateAssigneeRequest`."},"UpdateAutoEnrichmentConfigRequest":{"properties":{"trigger_on_insert":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Trigger On Insert","description":"Enrich every newly inserted record automatically. Turning this on starts ONGOING credit spend with no further call."}},"type":"object","title":"UpdateAutoEnrichmentConfigRequest","description":"Edit an auto-enrichment configuration."},"UpdateAutoEnrichmentSettingsRequest":{"properties":{"enabled":{"type":"boolean","title":"Enabled","default":true},"default_rule":{"type":"string","enum":["sticky","user_wins","mashup_wins"],"title":"Default Rule","default":"sticky"},"per_field_overrides":{"additionalProperties":{"type":"string","enum":["sticky","user_wins","mashup_wins"]},"type":"object","title":"Per Field Overrides"}},"type":"object","title":"UpdateAutoEnrichmentSettingsRequest","description":"Organisation-wide auto-enrichment for one record kind.\n\n`default_rule` decides who wins when enriched data disagrees with what is\non the record: `sticky` keeps the first value, `user_wins` never overwrites\na person's edit, `mashup_wins` lets enrichment overwrite."},"UpdateAvailabilityRequest":{"properties":{"availability":{"anyOf":[{"items":{"$ref":"#/components/schemas/AvailabilityInput"},"type":"array"},{"type":"null"}],"title":"Availability"},"overrides":{"anyOf":[{"items":{"$ref":"#/components/schemas/OverrideInput"},"type":"array"},{"type":"null"}],"title":"Overrides"}},"type":"object","title":"UpdateAvailabilityRequest"},"UpdateCallRequest":{"properties":{"call_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Call Status","description":"New status for the call."},"audio_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audio Url","description":"Where the recording lives."},"final_score":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Final Score","description":"Score for the call."},"duration_ms":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Duration Ms","description":"Call length in milliseconds."}},"type":"object","title":"UpdateCallRequest","description":"Amend a call record. Every field is optional and only what you send is written."},"UpdateCapabilitiesRequest":{"properties":{"phone_number":{"type":"string","title":"Phone Number","description":"The number to reconfigure, E.164."},"voice":{"type":"boolean","title":"Voice","description":"Answer inbound calls with a voice AI agent.","default":false},"dialer":{"type":"boolean","title":"Dialer","description":"Use the number for outbound dialing.","default":false}},"type":"object","required":["phone_number"],"title":"UpdateCapabilitiesRequest","description":"Switch a number between dialer and voice-AI answering.\n\nMirrors `phone_numbers.interfaces.fastapi.dtos.UpdateCapabilitiesRequest`.\n\nThe two flags are not independent in effect: the app derives the voice\nservice's `inbound_type` as `dialer` only when `dialer` is set and `voice`\nis not, and `ai` in every other combination."},"UpdateDestinationCalendarRequest":{"properties":{"integration":{"type":"string","title":"Integration","description":"Calendar integration key, e.g. `google_calendar`."},"external_id":{"type":"string","title":"External Id","description":"The calendar's id in the provider."},"credential_id":{"type":"integer","title":"Credential Id","description":"The connected-calendar credential to write through."},"primary_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Primary Email"},"use_calendar_email":{"type":"boolean","title":"Use Calendar Email","description":"Send invitations from the calendar's own address rather than the host's.","default":false}},"type":"object","required":["integration","external_id","credential_id"],"title":"UpdateDestinationCalendarRequest","description":"Where bookings for ONE event type are written."},"UpdateEmbedConfigRequest":{"properties":{"theme":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Theme"},"brand_color":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Brand Color"},"brand_color_dark":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Brand Color Dark"},"hide_event_type_details":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Hide Event Type Details"},"layout":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Layout"},"button_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Button Text"},"button_text_color":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Button Text Color"},"button_position":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Button Position"}},"type":"object","title":"UpdateEmbedConfigRequest","description":"How the embedded booking widget looks. Every field is optional."},"UpdateEnrichmentFieldRequest":{"properties":{"value":{"title":"Value","description":"The new value. Null clears the cell."},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"record_type":{"type":"string","enum":["contact","company"],"title":"Record Type","default":"contact"}},"type":"object","required":["value"],"title":"UpdateEnrichmentFieldRequest","description":"Hand-edit one enriched cell. No provider is called and nothing is charged."},"UpdateEventTypeRequest":{"properties":{"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"slug":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slug"},"length":{"anyOf":[{"type":"integer","maximum":525600.0,"minimum":5.0},{"type":"null"}],"title":"Length"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"locations":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Locations"},"booking_fields":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Booking Fields"},"scheduling_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Scheduling Type"},"schedule_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Schedule Id"},"time_zone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Time Zone"},"hidden":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Hidden"},"requires_confirmation":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Requires Confirmation"},"minimum_booking_notice":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Minimum Booking Notice"},"before_event_buffer":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Before Event Buffer"},"after_event_buffer":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"After Event Buffer"},"slot_interval":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Slot Interval"},"seats_per_time_slot":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Seats Per Time Slot"},"disable_guests":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Disable Guests"},"disable_cancelling":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Disable Cancelling"},"disable_rescheduling":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Disable Rescheduling"},"recurring_event":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Recurring Event"},"period_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Period Type"},"period_start_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Period Start Date"},"period_end_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Period End Date"},"period_days":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Period Days"},"success_redirect_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Success Redirect Url"},"event_color":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Event Color"},"event_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Event Name"},"layouts":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Layouts"},"default_layout":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Default Layout"},"metadata":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Metadata"},"use_common_schedule":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Use Common Schedule"}},"type":"object","title":"UpdateEventTypeRequest"},"UpdateFindPeopleConfigRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"search_filters":{"anyOf":[{"items":{"$ref":"#/components/schemas/SearchFilterDto"},"type":"array"},{"type":"null"}],"title":"Search Filters"},"column_mappings":{"anyOf":[{"items":{"$ref":"#/components/schemas/ColumnMappingDto"},"type":"array"},{"type":"null"}],"title":"Column Mappings"},"company_identifier_column":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Identifier Column"},"max_people_per_company":{"anyOf":[{"type":"integer","maximum":50.0,"minimum":1.0},{"type":"null"}],"title":"Max People Per Company"},"max_total_people":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Max Total People"},"destination_list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Destination List Id"},"skip_existing_in_destination":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Skip Existing In Destination"},"skip_across_companies":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Skip Across Companies"},"auto_import":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Auto Import"},"is_active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Active"}},"type":"object","title":"UpdateFindPeopleConfigRequest","description":"Edit a people-search configuration. Omitted fields are unchanged."},"UpdateFormulaConfigRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"field_to_enrich":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Field To Enrich"},"data_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Data Type"},"config":{"anyOf":[{"$ref":"#/components/schemas/FormulaConfigDto"},{"type":"null"}]}},"type":"object","title":"UpdateFormulaConfigRequest","description":"Edit a formula column. Omitted fields are left alone."},"UpdateGlobalContextRequest":{"properties":{"content":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Content","description":"New document body. Stored at meta_data.content. Omit to leave unchanged."},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"New document status (e.g. 'completed', 'draft'). Omit to leave unchanged."}},"type":"object","title":"UpdateGlobalContextRequest","description":"Body for PATCH /global-context/documents/{doc_id}.\n\nPartial update: send only the fields you want to change. At least one of\n``content`` / ``status`` must be present."},"UpdateHtmlRequest":{"properties":{"html":{"type":"string","title":"Html"}},"type":"object","required":["html"],"title":"UpdateHtmlRequest","description":"Raw HTML save from the code editor. Deterministic, spends nothing."},"UpdateIcpRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"New ICP name."},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"New description."},"firmographics":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Firmographics","description":"New firmographic criteria."},"tech_stack":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Tech Stack","description":"New technology signals."},"buying_signals":{"anyOf":[{"items":{},"type":"array"},{"type":"null"}],"title":"Buying Signals","description":"New list of buying-intent signals."},"estimated_market_size":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Estimated Market Size","description":"New estimated market-size count."}},"type":"object","title":"UpdateIcpRequest","description":"Body for PATCH /icps/{icp_id}. Partial - send only the fields to change.\n\nAt least one field must be present. Archiving is a separate lifecycle action\n(POST /icps/{icp_id}/archive), matching the internal Studio split."},"UpdateKeywordRequest":{"properties":{"keyword":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Keyword","description":"The listener's name. Must not be blank."},"search_filters":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Search Filters","description":"FULL REPLACEMENT of the filter object, not a merge - filters left out are dropped. `window_days` must be 1-365 and `contacts_per_company` 1-50 when present."},"watchlist_source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Watchlist Source","description":"Talent Moves watchlist scope, as a JSON-encoded string."}},"type":"object","title":"UpdateKeywordRequest","description":"Partial update of a HIRING listener (`jobs` / `job_changes` keyword).\n\nOmitted fields are left alone. The app refuses a plain intent keyword here\nwith a 404; its filters are replaced with `POST /intent/keywords/{id}/filters`."},"UpdateLandingPageRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"slug":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slug"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"settings":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Settings"}},"type":"object","title":"UpdateLandingPageRequest","description":"Metadata only - name, slug, description, settings. Spends nothing."},"UpdateLibraryDocumentRequest":{"properties":{"display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display Name"},"content":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Content"},"folder_path":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Folder Path"},"meta_data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Meta Data"}},"type":"object","title":"UpdateLibraryDocumentRequest","description":"Partial update. New `content` is re-embedded."},"UpdateLifecyclesRequest":{"properties":{"entries":{"items":{"$ref":"#/components/schemas/LifecycleEntryRequest"},"type":"array","title":"Entries"}},"type":"object","required":["entries"],"title":"UpdateLifecyclesRequest","description":"REPLACES the whole `entries` array. A stage left out is DELETED.\n\nThis is a PUT in the app and a PUT here for that reason: it is not a\nmerge. Read `GET /lifecycle-stages` first and send the full list back with\nyour change applied."},"UpdateListPipelineRequest":{"properties":{"name":{"type":"string","maxLength":255,"minLength":1,"title":"Name"},"steps":{"items":{"$ref":"#/components/schemas/ListPipelineStep"},"type":"array","maxItems":20,"minItems":1,"title":"Steps"},"enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Enabled"}},"type":"object","required":["name","steps"],"title":"UpdateListPipelineRequest","description":"Replace a list pipeline's definition. `enabled` omitted keeps its state."},"UpdateLocationRequest":{"properties":{"selected_location":{"anyOf":[{"$ref":"#/components/schemas/LocationItem"},{"type":"null"}]},"selected_conferencing":{"anyOf":[{"$ref":"#/components/schemas/LocationItem"},{"type":"null"}]},"notify_attendees":{"type":"boolean","title":"Notify Attendees","default":true},"location":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Location"}},"type":"object","title":"UpdateLocationRequest","description":"Change a booking's location and/or conferencing.\n\nSend only the field you change: an omitted field is left as is, and ``null``\nclears it. ``selected_location`` is a physical, phone or custom location;\n``selected_conferencing`` is a meeting link or a conferencing app (a new\nmeeting room is created for zoom, roam_auto, ms_teams and google_meet).\n``location`` is deprecated: a plain address, kept for older clients."},"UpdateMashupSyncPolicyRequest":{"properties":{"policy":{"$ref":"#/components/schemas/MashupSyncPolicy"},"expected_version":{"type":"integer","minimum":0.0,"title":"Expected Version","description":"Version this edit was based on."}},"type":"object","required":["policy","expected_version"],"title":"UpdateMashupSyncPolicyRequest","description":"Replace the record-sync policy.\n\n`expected_version` is the version the caller READ. A stale value is\nrejected rather than applied, so two editors cannot silently overwrite each\nother's policy - which on this object decides what gets overwritten on\nevery record in the org."},"UpdateMasterListConfigRequest":{"properties":{"source_list_ids":{"items":{"type":"integer"},"type":"array","title":"Source List Ids"},"include_all_sources":{"type":"boolean","title":"Include All Sources","default":false}},"type":"object","title":"UpdateMasterListConfigRequest","description":"Replace a master list's sources.\n\nA REPLACE, not a merge: a source you omit stops feeding the master list.\nSaved synchronously, and the re-sync runs in the background afterwards, so\na 200 here means the config is stored, not that the membership has caught\nup."},"UpdateMeetingRequest":{"properties":{"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"start_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Start At"},"end_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"End At"},"location":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Location"},"contact_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Contact Ids"},"company_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Company Ids"},"deal_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Deal Ids"},"user_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Id"}},"type":"object","title":"UpdateMeetingRequest"},"UpdateMemberRoleRequest":{"properties":{"role":{"type":"string","enum":["ADMIN","MEMBER"],"title":"Role"}},"additionalProperties":false,"type":"object","required":["role"],"title":"UpdateMemberRoleRequest","description":"A member's SCHEDULING role - not their graph8 organisation role."},"UpdateMyMeetingRequest":{"properties":{"notes":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Notes"},"client_contact_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Client Contact Name"},"client_contact_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Client Contact Email"}},"type":"object","title":"UpdateMyMeetingRequest","description":"Employee-side meeting edit — notes + client-contact fields only.\n\nMirrors ``UpdateMyMeetingRequest`` in ``self_service_router`` exactly,\nwhich in turn is bounded by the ``SdrMeeting`` ORM columns\n(``shared/infrustructure/db/cdp/models/sdr_meeting.py``): only ``notes``,\n``client_contact_name`` and ``client_contact_email`` exist. The field\nnames here are the raw column names because the update is applied via\n``update(SdrMeeting).values(**updates)`` with no whitelist/rename step —\nan unknown key (the old ``contact_name``/``contact_phone``/``contact_title``\n/``contact_company``/``contact_linkedin_url`` set) raises SQLAlchemy\n\"Unconsumed column names\" inside the handler and 500s. Lifecycle fields\n(status, meeting_date, meeting_type, hiring_id) are intentionally not\neditable — those are calendar-driven client-side fields."},"UpdateNewsletterRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Name"},"goal":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Goal","description":"What the newsletter is for. Steers AI drafting."},"audience_list_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience List Id","description":"The audience new subscribers are drawn from. Changing it does NOT move anybody who is already subscribed."}},"type":"object","title":"UpdateNewsletterRequest","description":"Rename a newsletter, restate its goal, or point it at a different list."},"UpdateNewsletterSettingsRequest":{"properties":{"sending_domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sending Domain","description":"Must be verified first - see `settings/verify-domain`."},"default_sender_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Default Sender Name"},"default_sender_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Default Sender Email"},"default_reply_to":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Default Reply To"},"double_opt_in":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Double Opt In","description":"The ACTIVE double-opt-in flag the send pipeline reads. Legacy: a `true` written here is routed to `double_opt_in_intent` and the active flag is auto-promoted once the domain and sender are ready."},"double_opt_in_intent":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Double Opt In Intent","description":"The REQUEST for double opt-in, independent of readiness. Set this rather than `double_opt_in` - it is promoted automatically."},"skip_unverified_subscribers":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Skip Unverified Subscribers"},"auto_verify_on_import":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Auto Verify On Import"}},"type":"object","title":"UpdateNewsletterSettingsRequest","description":"Who a newsletter sends as, and how strict its opt-in is."},"UpdateOrgSettingsRequest":{"properties":{"logo_url":{"anyOf":[{"type":"string","maxLength":2083,"minLength":1,"format":"uri"},{"type":"null"}],"title":"Logo Url"},"brand_color":{"anyOf":[{"type":"string","pattern":"^#[0-9a-fA-F]{6}$"},{"type":"null"}],"title":"Brand Color","description":"Six-digit hex including the leading `#`, e.g. `#1a2b3c`."},"booking_page_theme":{"anyOf":[{"type":"string","enum":["light","dark","auto"]},{"type":"null"}],"title":"Booking Page Theme"},"hide_branding":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Hide Branding","description":"Remove the graph8 mark from the booking page."}},"additionalProperties":false,"type":"object","title":"UpdateOrgSettingsRequest","description":"Branding for the public booking page.\n\nCLOSED, mirroring the app: these land in a JSONB configuration column and\nthe app forbids extra keys so nothing can be smuggled into it. `logo_url`\nis an `HttpUrl` because the app's is - typed `str` here it would pass this\nlayer and then fail inside the proxy as a 500."},"UpdateOutOfOfficeRequest":{"properties":{"start":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Start"},"end":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"End"},"notes":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Notes"},"public_note":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Public Note"},"to_user_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"To User Id"},"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason"},"time_zone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Time Zone"}},"type":"object","title":"UpdateOutOfOfficeRequest"},"UpdatePageRequest":{"properties":{"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title"},"content_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Content Type"},"content_status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Content Status"},"primary_keyword":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Primary Keyword"},"body_content":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Body Content"}},"type":"object","title":"UpdatePageRequest","description":"Edit an inventory page. Spends nothing."},"UpdatePersonaRequest":{"properties":{"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title","description":"New persona title."},"priority":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Priority","description":"New display priority."},"confidence":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Confidence","description":"New confidence label."},"why_target":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Why Target","description":"New 'why target' text."},"key_signals":{"anyOf":[{"items":{},"type":"array"},{"type":"null"}],"title":"Key Signals","description":"New list of buying/intent signals."},"expected_receptivity":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Expected Receptivity","description":"New expected-receptivity note."},"campaign_approach":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Approach","description":"New campaign approach."},"recommended_goal":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Recommended Goal","description":"New recommended goal."},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"New status (e.g. 'active', 'archived')."}},"type":"object","title":"UpdatePersonaRequest","description":"Body for PATCH /personas/{persona_id}. Partial - send only fields to change.\n\nAt least one field must be present. Passing status='archived' is equivalent to\ncalling POST /personas/{persona_id}/archive."},"UpdateProgrammaticCampaignRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"data_source_type":{"anyOf":[{"type":"string","enum":["list","workbench","csv","seo_import"]},{"type":"null"}],"title":"Data Source Type"},"data_source_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Data Source Id"},"data_source_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Data Source Name"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"slug_template":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slug Template"},"variable_config":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Variable Config"},"settings":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Settings"}},"type":"object","title":"UpdateProgrammaticCampaignRequest","description":"Partial update. Changing the source or template marks pages for regeneration."},"UpdateQualificationTemplateRequest":{"properties":{"name":{"type":"string","maxLength":120,"minLength":1,"title":"Name"},"description":{"type":"string","maxLength":500,"title":"Description"},"prompt":{"type":"string","maxLength":30000,"minLength":100,"title":"Prompt"}},"type":"object","required":["name","description","prompt"],"title":"UpdateQualificationTemplateRequest","description":"Edit a qualification template's wording."},"UpdateRedialStateRequest":{"properties":{"redial_state":{"anyOf":[{"$ref":"#/components/schemas/RedialState"},{"type":"null"}]},"reset":{"type":"boolean","title":"Reset","default":false}},"type":"object","title":"UpdateRedialStateRequest","description":"Mirrors `UpdateRedialStateRequest`. Bookkeeping - dials nobody."},"UpdateResearchReportRequest":{"properties":{"markdown_content":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Markdown Content","description":"New rendered markdown body. Omit to leave unchanged. Triggers RAG re-index."},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"New report status. A report already 'completed'/'approved' can only move between those two states (done reports stay done)."}},"type":"object","title":"UpdateResearchReportRequest","description":"Body for PATCH /research-reports/{report_id}.\n\nPartial update: send only what you want to change. At least one of\n``markdown_content`` / ``status`` must be present."},"UpdateRoutingFormRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":255,"minLength":1},{"type":"null"}],"title":"Name"},"slug":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slug"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"fields":{"anyOf":[{"items":{"$ref":"#/components/schemas/RoutingFormField"},"type":"array"},{"type":"null"}],"title":"Fields"},"routes":{"anyOf":[{"items":{"$ref":"#/components/schemas/RoutingFormRouteInput"},"type":"array"},{"type":"null"}],"title":"Routes"},"disabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Disabled"}},"type":"object","title":"UpdateRoutingFormRequest"},"UpdateSavedFilterRequest":{"properties":{"title":{"anyOf":[{"type":"string","maxLength":120,"minLength":1},{"type":"null"}],"title":"Title"},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description","description":"Null CLEARS this one, unlike the others."},"state":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"State"}},"additionalProperties":false,"type":"object","title":"UpdateSavedFilterRequest","description":"Change a saved view.\n\n`null` means LEAVE ALONE for every field except `description`, where it is\na legitimate clear. The app draws that distinction and this mirrors it."},"UpdateScheduleProfileRequest":{"properties":{"time_zone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Time Zone","description":"IANA timezone, e.g. `Europe/London`."},"week_start":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Week Start"},"time_format":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Time Format","description":"12 or 24."},"buffer_time":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Buffer Time","description":"Minutes held either side of a booking."},"default_schedule_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Default Schedule Id"},"username":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Username","description":"Personal booking-URL slug. GLOBALLY unique across graph8 and claimed atomically, so a rename can lose the race and come back as a conflict."},"hide_calendar_from_org":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Hide Calendar From Org","description":"Hide the caller's external calendars from teammates' org-wide overlay."}},"type":"object","title":"UpdateScheduleProfileRequest","description":"The key owner's own scheduling preferences."},"UpdateScheduleRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"time_zone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Time Zone"},"is_default":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Default"},"availability":{"anyOf":[{"items":{"$ref":"#/components/schemas/AvailabilityInput"},"type":"array"},{"type":"null"}],"title":"Availability"},"overrides":{"anyOf":[{"items":{"$ref":"#/components/schemas/OverrideInput"},"type":"array"},{"type":"null"}],"title":"Overrides"}},"type":"object","title":"UpdateScheduleRequest"},"UpdateSectionRequest":{"properties":{"content":{"additionalProperties":true,"type":"object","title":"Content"}},"type":"object","required":["content"],"title":"UpdateSectionRequest","description":"Replace one section's content block. Deterministic, spends nothing."},"UpdateSelectedCalendarsRequest":{"properties":{"scope":{"type":"string","enum":["account","event_type"],"title":"Scope"},"entries":{"items":{"$ref":"#/components/schemas/SelectedCalendarEntry"},"type":"array","title":"Entries"}},"type":"object","required":["scope"],"title":"UpdateSelectedCalendarsRequest","description":"Which calendars are checked for conflicts on ONE event type.\n\n`scope` is a bare `str` in the app with its two values in a comment. It is\nclosed here, so a typo is a 422 rather than whatever the handler does with\nan unknown scope."},"UpdateSendingScheduleRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string","maxLength":1024},{"type":"null"}],"title":"Description"},"config":{"anyOf":[{"$ref":"#/components/schemas/SendingWeek"},{"type":"null"}]},"timezone":{"anyOf":[{"type":"string","maxLength":128},{"type":"null"}],"title":"Timezone"}},"type":"object","title":"UpdateSendingScheduleRequest","description":"Change a sending schedule. Mirrors `PatchScheduleParams`."},"UpdateSequenceTemplateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"textual_agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Textual Agent Name"},"voice_agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Voice Agent Name"},"schedule_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Schedule Id"},"appointment_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Appointment Id"},"steps":{"anyOf":[{"items":{"$ref":"#/components/schemas/SequenceTemplateStep"},"type":"array"},{"type":"null"}],"title":"Steps"}},"type":"object","title":"UpdateSequenceTemplateRequest","description":"Change a sequence template. Mirrors `PatchSequenceTemplatePayload`.\n\n`steps`, when sent, REPLACES the template's steps rather than merging."},"UpdateStagingAIFindPeopleCandidatesRequest":{"properties":{"candidate_ids":{"items":{"type":"string"},"type":"array","minItems":1,"title":"Candidate Ids"}},"type":"object","title":"UpdateStagingAIFindPeopleCandidatesRequest","description":"Mark candidates as skipped. Changes review state only."},"UpdateStepRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"channel":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Channel"},"mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mode"},"platform":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Platform"},"angle_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Angle Id"},"cta_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Cta Type"},"personalization_level":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Personalization Level"},"constraints":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Constraints"},"do_not_send_rules":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Do Not Send Rules"},"day":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Day"},"condition":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Condition"},"stop_on_reply":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Stop On Reply"}},"type":"object","title":"UpdateStepRequest"},"UpdateStepTemplateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"step_type":{"anyOf":[{"type":"string","enum":["PHONE","EMAIL","MANUAL_DIALER","HEYREACH","NETRION","SMS","WHATSAPP"]},{"type":"null"}],"title":"Step Type"},"step_data":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Step Data"}},"type":"object","title":"UpdateStepTemplateRequest","description":"Change a step template. Mirrors `PatchStepTemplatePayload`.\n\nThere is no `input_type` here because the app's patch has none: a\ntemplate's input type is fixed at creation."},"UpdateSurveyRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Name"},"question_text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Question Text"},"thank_you_copy":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Thank You Copy"},"template_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Template Id"},"delivery_channel":{"anyOf":[{"type":"string","pattern":"^(email|bridge|in_app)$"},{"type":"null"}],"title":"Delivery Channel"},"is_active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Active"}},"type":"object","title":"UpdateSurveyRequest"},"UpdateTextRequest":{"properties":{"element_id":{"type":"string","title":"Element Id"},"new_html":{"type":"string","title":"New Html"}},"type":"object","required":["element_id","new_html"],"title":"UpdateTextRequest","description":"Set one element's inner HTML directly. No AI, spends nothing."},"UpdateTriggerRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"conditions":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Conditions"},"action_config":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Action Config"},"enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Enabled"}},"type":"object","title":"UpdateTriggerRequest","description":"Edit an automation trigger. Every field is optional; omitted means unchanged."},"UpdateWarmupSettingsRequest":{"properties":{},"additionalProperties":true,"type":"object","title":"UpdateWarmupSettingsRequest","description":"Change how an already-running warmup behaves.\n\nOPEN (`extra=\"allow\"`), and deliberately: the app types this parameter as\na bare `Dict[str, Any]` and forwards it to the warmup provider untouched.\nThe accepted keys differ per provider and change with them, so a closed\nmirror here would reject a setting the provider supports - and the app\nwould have accepted it."},"UpdateWaterfallConfigRequest":{"properties":{"config":{"$ref":"#/components/schemas/WaterfallConfig"}},"type":"object","required":["config"],"title":"UpdateWaterfallConfigRequest","description":"Replace a waterfall's definition."},"UpdateWorkbenchPipelineRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"start":{"anyOf":[{"$ref":"#/components/schemas/PipelineStartConfig"},{"type":"null"}]},"steps":{"anyOf":[{"items":{"$ref":"#/components/schemas/WorkbenchPipelineStep"},"type":"array"},{"type":"null"}],"title":"Steps"},"enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Enabled"}},"type":"object","title":"UpdateWorkbenchPipelineRequest","description":"Edit a workbench pipeline. Omitted fields are left alone."},"UpdateWorkflowRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":255,"minLength":1},{"type":"null"}],"title":"Name"},"trigger":{"anyOf":[{"type":"string","enum":["new_booking","before_event","after_event","booking_cancelled","booking_rescheduled"]},{"type":"null"}],"title":"Trigger"},"time":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Time"},"time_unit":{"anyOf":[{"type":"string","enum":["minutes","hours","days"]},{"type":"null"}],"title":"Time Unit"},"is_active_on_all":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Active On All"},"event_type_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Event Type Ids"},"steps":{"anyOf":[{"items":{"$ref":"#/components/schemas/WorkflowStepInput"},"type":"array","maxItems":20,"minItems":1},{"type":"null"}],"title":"Steps"}},"type":"object","title":"UpdateWorkflowRequest"},"UrlCompaniesRequest":{"properties":{"url":{"type":"string","title":"Url","description":"Canonical page_url (no scheme, no www)"},"days":{"type":"integer","maximum":365.0,"minimum":1.0,"title":"Days","default":90},"limit":{"type":"integer","maximum":500.0,"minimum":1.0,"title":"Limit","default":200}},"type":"object","required":["url"],"title":"UrlCompaniesRequest"},"UsageBalanceResponse":{"properties":{"customer_id":{"type":"string","title":"Customer Id","description":"Org / customer id the credits belong to"},"credits":{"type":"number","title":"Credits","description":"Total credit balance"},"held_credits":{"type":"number","title":"Held Credits","description":"Credits currently on hold"},"available_credits":{"type":"number","title":"Available Credits","description":"Spendable credits (credits - held)"},"total_earned":{"type":"number","title":"Total Earned","description":"Lifetime credits earned"},"total_used":{"type":"number","title":"Total Used","description":"Lifetime credits used"}},"type":"object","required":["customer_id","credits","held_credits","available_credits","total_earned","total_used"],"title":"UsageBalanceResponse","description":"An org's current credit balance + lifetime totals."},"UsageSummaryResponse":{"properties":{"app_id":{"type":"string","title":"App Id"},"period":{"type":"string","title":"Period","description":"Calendar month, `YYYY-MM`."},"total_credits":{"type":"integer","title":"Total Credits"},"event_count":{"type":"integer","title":"Event Count"},"per_client_credits":{"additionalProperties":{"type":"integer"},"type":"object","title":"Per Client Credits","description":"Credits per CLIENT org — whose data was touched, not who paid. The builder pays for all of them."},"gross_credits":{"type":"integer","title":"Gross Credits","description":"Undiscounted list total for the period. `gross_credits - discount_credits == total_credits`.","default":0},"discount_credits":{"type":"integer","title":"Discount Credits","description":"Everything deducted from list: the builder discount AND any hard-cap clamp. One compound number, not 'the 25%'.","default":0},"per_payer_credits":{"additionalProperties":{"type":"integer"},"type":"object","title":"Per Payer Credits","description":"Net credits per BILLING org, who pays. The mirror of `per_client_credits`, which is whose data was touched."},"per_operation_credits":{"additionalProperties":{"type":"integer"},"type":"object","title":"Per Operation Credits","description":"Net credits per operation id, so you can see which calls cost money."}},"type":"object","required":["app_id","period","total_credits","event_count"],"title":"UsageSummaryResponse","description":"Credits an app consumed in one calendar month. Mirrors `UsageSummaryDto`."},"UsageTransactionResponse":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id","description":"Transaction id"},"type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Type","description":"Transaction type (e.g. 'usage', 'purchase')"},"amount":{"type":"number","title":"Amount","description":"Credit delta (negative = spend)","default":0.0},"service":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Service","description":"Service the charge was for (e.g. 'ai_enrichment')"},"quantity":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Quantity"},"llm_tier":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Llm Tier","description":"g8_t1 / g8_t2 / g8_t3 when an LLM charge"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"}},"type":"object","title":"UsageTransactionResponse","description":"A single credit-ledger transaction."},"UseTemplateRequest":{"properties":{"newsletter_id":{"type":"string","format":"uuid","title":"Newsletter Id","description":"Which newsletter the draft issue is created on."}},"type":"object","required":["newsletter_id"],"title":"UseTemplateRequest","description":"Turn a template into a new draft issue on a newsletter."},"UuidFilterGroupDto":{"properties":{"in":{"items":{"type":"string","maxLength":512},"type":"array","maxItems":1000,"title":"In"},"not":{"type":"boolean","title":"Not","default":false}},"additionalProperties":false,"type":"object","title":"UuidFilterGroupDto","description":"`pipeline` / `stage` — `CBDeal.pipeline_id` and `.stage_id` are real\n`PostgresUUID` columns, so a non-UUID can only ever fail open."},"ValidateCreditsRequest":{"properties":{"record_count":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Record Count","description":"Direct record count."},"mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mode","description":"'bulk' or 'column'."},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"enrichment_mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Enrichment Mode","description":"'first_10', 'all' or 'error_only'."},"filter_model":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Filter Model"},"sort_model":{"anyOf":[{"items":{"additionalProperties":{"type":"string"},"type":"object"},"type":"array"},{"type":"null"}],"title":"Sort Model"},"record_ids":{"anyOf":[{"items":{"anyOf":[{"type":"integer"},{"type":"string"},{"type":"string","format":"uuid"}]},"type":"array"},{"type":"null"}],"title":"Record Ids"},"visible_record_ids":{"anyOf":[{"items":{"anyOf":[{"type":"integer"},{"type":"string"},{"type":"string","format":"uuid"}]},"type":"array"},{"type":"null"}],"title":"Visible Record Ids"},"context_record_ids":{"anyOf":[{"items":{"anyOf":[{"type":"integer"},{"type":"string"},{"type":"string","format":"uuid"}]},"type":"array"},{"type":"null"}],"title":"Context Record Ids"},"max_records":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Max Records"},"credits_per_record":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Credits Per Record","description":"Deprecated. Pricing is computed server-side and this is ignored."},"group_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Group Id","description":"AI enrichment group id."}},"type":"object","title":"ValidateCreditsRequest","description":"Price an AI enrichment before running it. Charges nothing."},"ValidateManifestResponse":{"properties":{"valid":{"type":"boolean","title":"Valid"},"summary":{"anyOf":[{"$ref":"#/components/schemas/ManifestSummary"},{"type":"null"}]},"issues":{"items":{"$ref":"#/components/schemas/ManifestIssueResponse"},"type":"array","title":"Issues"}},"type":"object","required":["valid"],"title":"ValidateManifestResponse","description":"A dry run. `valid` is the answer; `issues` is why not.\n\n200 either way. A syntactically well-formed request that asks \"is this\nmanifest valid\" and gets the answer \"no\" has been served correctly, and a\n422 would make a builder's linter treat a working call as a transport\nfailure."},"ValidateWaterfallCreditsRequest":{"properties":{"record_count":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Record Count","description":"Direct record count."},"mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mode","description":"'bulk' or 'column'."},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"enrichment_mode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Enrichment Mode","description":"'first_10', 'all' or 'error_only'."},"filter_model":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Filter Model"},"sort_model":{"anyOf":[{"items":{"additionalProperties":{"type":"string"},"type":"object"},"type":"array"},{"type":"null"}],"title":"Sort Model"},"record_ids":{"anyOf":[{"items":{"anyOf":[{"type":"integer"},{"type":"string"},{"type":"string","format":"uuid"}]},"type":"array"},{"type":"null"}],"title":"Record Ids"},"visible_record_ids":{"anyOf":[{"items":{"anyOf":[{"type":"integer"},{"type":"string"},{"type":"string","format":"uuid"}]},"type":"array"},{"type":"null"}],"title":"Visible Record Ids"},"context_record_ids":{"anyOf":[{"items":{"anyOf":[{"type":"integer"},{"type":"string"},{"type":"string","format":"uuid"}]},"type":"array"},{"type":"null"}],"title":"Context Record Ids"},"max_records":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Max Records"},"credits_per_record":{"anyOf":[{"type":"integer","minimum":1.0},{"type":"null"}],"title":"Credits Per Record","description":"Deprecated. Pricing is computed server-side and this is ignored."},"column_id":{"type":"string","title":"Column Id","description":"Waterfall enrichment column id."}},"type":"object","required":["column_id"],"title":"ValidateWaterfallCreditsRequest","description":"Price a waterfall enrichment before running it. Charges nothing."},"ValidationError":{"properties":{"loc":{"items":{"anyOf":[{"type":"string"},{"type":"integer"}]},"type":"array","title":"Location"},"msg":{"type":"string","title":"Message"},"type":{"type":"string","title":"Error Type"}},"type":"object","required":["loc","msg","type"],"title":"ValidationError"},"VerdictReviewRequest":{"properties":{"thread_id":{"type":"string","maxLength":2048,"minLength":1,"title":"Thread Id"},"message_id":{"type":"string","maxLength":2048,"minLength":1,"title":"Message Id","description":"The verdict message id (provider id or RFC id)."},"decision":{"type":"string","enum":["confirm_reply","dismiss"],"title":"Decision"}},"type":"object","required":["thread_id","message_id","decision"],"title":"VerdictReviewRequest","description":"Resolve a reply verdict that needs a human decision."},"VerifyContactEmailAsyncRequest":{"properties":{"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id","description":"Restrict the selection to this list."},"allMatching":{"type":"boolean","title":"Allmatching","description":"Resolve the complete matching set server-side, not just a page.","default":false},"filterModel":{"additionalProperties":true,"type":"object","title":"Filtermodel","description":"Per-column filters, keyed by column name."},"segmentFilter":{"anyOf":[{"$ref":"#/components/schemas/SegmentFilterGroup"},{"type":"null"}],"description":"Advanced cross-column AND/OR filter tree."}},"type":"object","title":"VerifyContactEmailAsyncRequest","description":"Queue verification for a LIST or a filtered selection.\n\nSPENDS CREDITS, and unlike the synchronous route the size is not known\nwhen the call returns - `all_matching` resolves the selection server-side."},"VerifyContactEmailRequest":{"properties":{"contact_pks":{"items":{"type":"integer"},"type":"array","maxItems":1000,"title":"Contact Pks","description":"Contact primary keys (max 1000). Empty verifies nothing."}},"type":"object","title":"VerifyContactEmailRequest","description":"Re-check the deliverability of a named batch of contacts' emails.\n\nSPENDS CREDITS: each address is sent to the email-verification service.\nUse the async variant for a whole list or a filtered selection."},"VerifyDomainRequest":{"properties":{"domain":{"type":"string","title":"Domain","description":"Sending subdomain, e.g. `updates.acme.com`."}},"type":"object","required":["domain"],"title":"VerifyDomainRequest","description":"Start verification of a sending domain."},"VerifyEmailRequest":{"properties":{"email":{"type":"string","title":"Email","description":"Email address to verify"}},"type":"object","required":["email"],"title":"VerifyEmailRequest"},"VerifyEmailResponse":{"additionalProperties":true,"type":"object"},"VerifyKnowledgeRequest":{"properties":{"approve":{"type":"boolean","title":"Approve"},"authority":{"type":"string","maxLength":255,"minLength":1,"title":"Authority"}},"type":"object","required":["approve","authority"],"title":"VerifyKnowledgeRequest","description":"Approve (or reject) a proposed concept, naming who vouches for it."},"VerifySurveyDomainRequest":{"properties":{"domain":{"type":"string","minLength":1,"title":"Domain","description":"The sending domain or subdomain, e.g. `feedback.acme.com`."}},"type":"object","required":["domain"],"title":"VerifySurveyDomainRequest","description":"Start verification of a survey sending domain."},"VideoClipPromptInputs":{"properties":{"subject":{"type":"string","maxLength":500,"minLength":3,"title":"Subject"},"setting":{"anyOf":[{"type":"string","maxLength":300},{"type":"null"}],"title":"Setting"},"style":{"anyOf":[{"type":"string","maxLength":40},{"type":"null"}],"title":"Style"},"camera":{"anyOf":[{"type":"string","maxLength":40},{"type":"null"}],"title":"Camera"},"lighting":{"anyOf":[{"type":"string","maxLength":120},{"type":"null"}],"title":"Lighting"},"negative":{"anyOf":[{"type":"string","maxLength":300},{"type":"null"}],"title":"Negative"}},"type":"object","required":["subject"],"title":"VideoClipPromptInputs","description":"The structured shot description. `subject` is the only required field."},"VideoPromptEnhanceRequest":{"properties":{"prompt_inputs":{"$ref":"#/components/schemas/VideoClipPromptInputs"}},"type":"object","required":["prompt_inputs"],"title":"VideoPromptEnhanceRequest","description":"Turn the structured shot form into one generation prompt. SPENDS CREDIT (small)."},"VideoShot":{"properties":{"clip_id":{"type":"string","title":"Clip Id"},"in_s":{"anyOf":[{"type":"number","minimum":0.0},{"type":"null"}],"title":"In S"},"out_s":{"anyOf":[{"type":"number","exclusiveMinimum":0.0},{"type":"null"}],"title":"Out S"}},"type":"object","required":["clip_id"],"title":"VideoShot","description":"One clip on the storyboard, optionally trimmed."},"VideoStoryboard":{"properties":{"shots":{"items":{"$ref":"#/components/schemas/VideoShot"},"type":"array","maxItems":5,"title":"Shots"},"copy":{"additionalProperties":{"type":"string"},"type":"object","title":"Copy","description":"Copy slot id (headline, subline, cta, ...) -> text."}},"type":"object","title":"VideoStoryboard","description":"The ordered shots (1-5) and the copy for the template's text slots."},"Visibility":{"type":"string","enum":["private","org"],"title":"Visibility","description":"Who can apply a view. Only the creator can update or delete it."},"VisitorCompanyResponse":{"properties":{"company_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Name"},"company_domain":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Domain"},"industry":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Industry"},"employee_count":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Employee Count"},"city":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"City"},"country":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Country"},"confidence":{"type":"number","title":"Confidence","default":0.0}},"type":"object","title":"VisitorCompanyResponse"},"VisitorContactEvent":{"properties":{"page_title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Page Title"},"page_host":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Page Host"},"page_path":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Page Path"},"visit_time":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Visit Time"}},"type":"object","title":"VisitorContactEvent","description":"One page view by one identified contact."},"VisitorContactEvents":{"properties":{"events":{"items":{"$ref":"#/components/schemas/VisitorContactEvent"},"type":"array","title":"Events"}},"type":"object","title":"VisitorContactEvents","description":"Everything one identified contact did on the website, newest first."},"VisitorEventPage":{"properties":{"events":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Events"},"total":{"type":"integer","title":"Total","default":0},"page":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Page"},"limit":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Limit"}},"additionalProperties":true,"type":"object","title":"VisitorEventPage","description":"A page of visitor events.\n\nRows are open dicts on purpose: each feed (contact, company, campaign, ad,\nlink) carries a different field set, and the tracker adds fields over\ntime. A pinned per-feed schema would silently drop whatever it had not\ncaught up on - and on an analytics surface a missing field reads as a\nmissing visit."},"VisitorListSyncJob":{"properties":{"job_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Job Id"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"}},"additionalProperties":true,"type":"object","title":"VisitorListSyncJob","description":"A campaign list sync job, or its status. Open-shaped - the receipt grows with the job store."},"VisitorListSyncRequest":{"properties":{"sequencer_step_ids":{"items":{"type":"string"},"type":"array","maxItems":500,"minItems":1,"title":"Sequencer Step Ids","description":"Campaign (sequence) step ids whose visitors are synced into the campaign's list."}},"additionalProperties":false,"type":"object","required":["sequencer_step_ids"],"title":"VisitorListSyncRequest","description":"Which campaign steps' website visitors to sync into their campaign lists.\n\nThe app's body is a list of filter conditions, but its handler accepts\nEXACTLY ONE shape - a single `sequencer_step_id` / `in` condition with a\nnon-empty value - and 422s every other. This publishes that shape and\nnothing else; the proxy builds the one condition from it."},"VisitorScoreResponse":{"properties":{"engagement":{"type":"integer","title":"Engagement","default":0},"intent":{"type":"string","title":"Intent","default":"low"},"signals":{"items":{"type":"string"},"type":"array","title":"Signals","default":[]}},"type":"object","title":"VisitorScoreResponse"},"VisitorStatisticsResponse":{"properties":{"series":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Series"},"total":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Total"}},"additionalProperties":true,"type":"object","title":"VisitorStatisticsResponse","description":"Counts over the visitor stream.\n\n`companies` counts UNIQUE BY IP and `contacts` does not, so the two series\nare not comparable row for row - charting them on one axis as if they were\noverstates or understates one of them depending on traffic shape."},"VisitorStream":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"publicKeys":{"items":{"type":"string"},"type":"array","title":"Publickeys","description":"Public write keys. Named in the app's camelCase rather than re-cased here - the snippet reads this value verbatim, and renaming it would be a silent breakage in a copy-paste flow."}},"additionalProperties":true,"type":"object","title":"VisitorStream","description":"One tracking stream and the public keys the snippet sends with."},"VisitorStreamsResponse":{"properties":{"streams":{"items":{"$ref":"#/components/schemas/VisitorStream"},"type":"array","title":"Streams"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"VisitorStreamsResponse","description":"The tracking workspace's streams."},"VoiceAgentCreateRequest":{"properties":{"agent_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent Id","description":"Agent UUID. Auto-generated if omitted."},"agent_status":{"type":"string","enum":["active","inactive","archived"],"title":"Agent Status","description":"Initial status.","default":"active"},"role":{"type":"string","title":"Role","description":"Agent role (e.g. \"SDR\", \"AE\", \"Receptionist\", \"CSM\")."},"entity_type":{"type":"string","enum":["agent","twin"],"title":"Entity Type","description":"\"agent\" or \"twin\".","default":"agent"},"persona":{"$ref":"#/components/schemas/VoiceAgentPersona"},"identity":{"$ref":"#/components/schemas/VoiceAgentIdentity"},"knowledge":{"anyOf":[{"$ref":"#/components/schemas/VoiceAgentKnowledge"},{"type":"null"}],"description":"Attached knowledge collections."},"use_company_knowledge":{"type":"boolean","title":"Use Company Knowledge","description":"Also draw on the org-wide knowledge base.","default":true},"is_template":{"type":"boolean","title":"Is Template","description":"Save this as a reusable template rather than a live agent.","default":false},"template_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Template Id","description":"Template this agent was cloned from, if any."}},"type":"object","required":["role","persona","identity"],"title":"VoiceAgentCreateRequest","description":"Body for creating a voice agent or twin.\n\nOrg is pinned server-side from the API key - never read from the body.\n``created_by_email`` is likewise pinned to the calling principal (used\nupstream for one-twin-per-user enforcement and SDR/booking attribution);\nan org-wide API key has no per-human identity to attribute to beyond the\nkey itself, so it is set to the same identifier the dialer-session and\ncall routes already use for ``user_email``.\n\nDeliberately NOT exposed here (follow-up, not an oversight): twin-only\nfields ``tone_profile``, ``channels``, and ``persona_source_user_id``.\nThey only apply when ``entity_type=\"twin\"`` and none of this PR's\npriority surfaces (ad-hoc call, dialer sessions, dispositions) need them."},"VoiceAgentDetail":{"properties":{"id":{"type":"integer","title":"Id"},"agent_id":{"type":"string","title":"Agent Id"},"org_id":{"type":"string","title":"Org Id"},"agent_status":{"type":"string","title":"Agent Status"},"role":{"type":"string","title":"Role"},"entity_type":{"type":"string","title":"Entity Type"},"persona":{"$ref":"#/components/schemas/VoiceAgentPersona"},"identity":{"$ref":"#/components/schemas/VoiceAgentIdentity"},"knowledge":{"$ref":"#/components/schemas/VoiceAgentKnowledge"},"use_company_knowledge":{"type":"boolean","title":"Use Company Knowledge"},"is_template":{"type":"boolean","title":"Is Template"},"template_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Template Id"},"created_by_email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created By Email"},"created_at":{"anyOf":[{},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["id","agent_id","org_id","agent_status","role","entity_type","persona","identity","knowledge","use_company_knowledge","is_template"],"title":"VoiceAgentDetail","description":"Complete agent configuration, as returned by create/get/update."},"VoiceAgentIdentity":{"properties":{"phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone","description":"Phone number in E.164 format (e.g. +15551234567). Optional."},"voice":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Voice","description":"Voice ID (Cartesia voice_id or OpenAI voice name). Optional."},"calendar":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Calendar","description":"Calendar/event-type system ID. Optional."},"avatar_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Avatar Url","description":"URL of the agent's avatar image. Optional."}},"type":"object","title":"VoiceAgentIdentity","description":"Communication-channel identity for a voice agent (mirrors V2 ``IdentityV2``)."},"VoiceAgentKnowledge":{"properties":{"collections":{"items":{"type":"string"},"type":"array","title":"Collections","description":"Collection IDs (max 4)."}},"type":"object","title":"VoiceAgentKnowledge","description":"Knowledge-collection attachments for a voice agent."},"VoiceAgentListResponse":{"properties":{"agents":{"items":{"$ref":"#/components/schemas/VoiceAgentSummary"},"type":"array","title":"Agents"},"total_count":{"type":"integer","title":"Total Count","default":0},"page":{"type":"integer","title":"Page","default":1},"page_size":{"type":"integer","title":"Page Size","default":20},"total_pages":{"type":"integer","title":"Total Pages","default":0}},"type":"object","title":"VoiceAgentListResponse","description":"Paginated agent list."},"VoiceAgentPersona":{"properties":{"agent_name":{"type":"string","title":"Agent Name","description":"Display name of the agent."},"persona":{"type":"string","title":"Persona","description":"Personality and behavior description."},"formality_level":{"type":"number","maximum":1.0,"minimum":0.0,"title":"Formality Level","description":"0.0=casual, 1.0=formal."},"conciseness_level":{"type":"number","maximum":1.0,"minimum":0.0,"title":"Conciseness Level","description":"0.0=verbose, 1.0=brief."},"assertiveness_level":{"type":"number","maximum":1.0,"minimum":0.0,"title":"Assertiveness Level","description":"0.0=passive, 1.0=assertive."},"description":{"type":"string","title":"Description","description":"Brief summary of the agent's purpose."},"inbound_instructions":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Inbound Instructions","description":"Extra instructions for inbound calls."},"outbound_instructions":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Outbound Instructions","description":"Extra instructions for outbound calls."},"outbound_voicemail_prompt":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Outbound Voicemail Prompt","description":"Voicemail message this agent leaves."},"company_name_pronunciation":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Company Name Pronunciation","description":"TTS pronunciation override for the company name (e.g. 'Science' for 'CIENCE')."}},"type":"object","required":["agent_name","persona","formality_level","conciseness_level","assertiveness_level","description"],"title":"VoiceAgentPersona","description":"Persona / prompt configuration for a voice agent (mirrors V2 ``PersonaV2``)."},"VoiceAgentResponse":{"properties":{"agent":{"anyOf":[{"$ref":"#/components/schemas/VoiceAgentDetail"},{"type":"null"}]},"message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Message"}},"type":"object","title":"VoiceAgentResponse","description":"Envelope for single-agent operations (create / get / update)."},"VoiceAgentSummary":{"properties":{"id":{"type":"integer","title":"Id"},"agent_id":{"type":"string","title":"Agent Id"},"org_id":{"type":"string","title":"Org Id"},"agent_name":{"type":"string","title":"Agent Name"},"role":{"type":"string","title":"Role"},"agent_status":{"type":"string","title":"Agent Status"},"entity_type":{"type":"string","title":"Entity Type"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phone"},"voice":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Voice"},"calendar_event_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Calendar Event Id"},"avatar_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Avatar Url"},"has_knowledge":{"type":"boolean","title":"Has Knowledge","default":false},"use_company_knowledge":{"type":"boolean","title":"Use Company Knowledge","default":true},"collection_count":{"type":"integer","title":"Collection Count","default":0},"is_template":{"type":"boolean","title":"Is Template","default":false},"template_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Template Id"},"created_at":{"anyOf":[{},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["id","agent_id","org_id","agent_name","role","agent_status","entity_type"],"title":"VoiceAgentSummary","description":"One row from the agent list (full management shape - see also the\nlighter-weight ``DialerAgentSummary`` used by the dialer picker)."},"VoiceAgentUpdateRequest":{"properties":{"agent_status":{"anyOf":[{"type":"string","enum":["active","inactive","archived"]},{"type":"null"}],"title":"Agent Status"},"role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Role"},"persona":{"anyOf":[{"$ref":"#/components/schemas/VoiceAgentPersona"},{"type":"null"}]},"identity":{"anyOf":[{"$ref":"#/components/schemas/VoiceAgentIdentity"},{"type":"null"}]},"knowledge":{"anyOf":[{"$ref":"#/components/schemas/VoiceAgentKnowledge"},{"type":"null"}]},"use_company_knowledge":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Use Company Knowledge"},"is_template":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Template"}},"type":"object","title":"VoiceAgentUpdateRequest","description":"Body for partially updating a voice agent. Only supplied fields change."},"VoiceAssigneeRequest":{"properties":{"number":{"type":"string","title":"Number","description":"The number to reassign, E.164."},"assigned_to":{"type":"string","title":"Assigned To","description":"Email of the new assignee, or `\"\"` to clear it. Normalised by voice before storage so inbound ring targeting, the dialer assignee filter and per-rep stat redaction all compare equal."}},"type":"object","required":["number","assigned_to"],"title":"VoiceAssigneeRequest","description":"Point a number's voice-side assignment at someone else.\n\nMirrors `graph8_livekit.schemas.numbers.UpdateAssignee` minus `org_id`.\n\n`assigned_to` is REQUIRED but may be the empty string, which is how voice\nspells \"clear the assignment\" - its own normalisation passes falsy input\nthrough untouched for exactly that reason."},"VoiceCallStartRequest":{"properties":{"to_phone":{"type":"string","maxLength":16,"minLength":1,"title":"To Phone","description":"Number to call. Normalized server-side."},"from_phone":{"type":"string","maxLength":16,"minLength":9,"title":"From Phone","description":"Caller ID. Must be one of the org's numbers."},"agent_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent Id","description":"Voice agent UUID. Use GET /voice/agents to look up."},"entity_type":{"anyOf":[{"type":"string","enum":["agent","twin"]},{"type":"null"}],"title":"Entity Type","description":"\"agent\" or \"twin\". Optional."},"agent_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent Name","description":"Legacy V1 agent-name fallback.","default":"default_agent"},"first_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"First Name","description":"Contact first name, for the agent's context."},"last_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Name","description":"Contact last name, for the agent's context."},"email":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Email","description":"Contact email, for the agent's context."},"contact_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Contact Id","description":"CDP contact id, if this call is tied to a known contact."},"timezone":{"type":"string","title":"Timezone","description":"IANA timezone for the callee.","default":"America/New_York"},"campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Campaign Id","description":"Optional campaign id for attribution."},"studio_campaign_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Studio Campaign Id","description":"Optional Campaign Builder (Studio) campaign UUID."},"dry_run":{"type":"boolean","title":"Dry Run","description":"If true, the call is validated but not actually dispatched.","default":false},"event_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Event Id","description":"Appointments event-type id the agent can offer to book. Omit if this call has no booking flow."},"callback_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Callback Url","description":"Webhook notified with the call result on completion. Optional."}},"type":"object","required":["to_phone","from_phone"],"title":"VoiceCallStartRequest","description":"Body for dispatching one AI-agent call to an arbitrary number.\n\nNo dialer session or contact list required - this is the \"call this one\nnumber right now\" primitive (`voice/graph8_livekit/routers/call.py:19`).\nPlaces a REAL call and is billable; send an ``Idempotency-Key`` header to\nmake a retry safe (honored automatically by the Developer API's\nidempotency middleware on every POST - no extra body field needed)."},"VoiceCallStartResponse":{"properties":{"status":{"type":"string","title":"Status"},"message":{"type":"string","title":"Message"},"room_name":{"type":"string","title":"Room Name"}},"type":"object","required":["status","message","room_name"],"title":"VoiceCallStartResponse","description":"Echo of voice's ``AgentDispatchResponse``."},"VoiceCustomDispositionCreateRequest":{"properties":{"name":{"type":"string","maxLength":40,"minLength":1,"title":"Name"},"description":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Description"},"color":{"type":"string","title":"Color","description":"Hex value from voice's preset palette (e.g. '#10b981'). Invalid values 400."},"is_connected":{"type":"boolean","title":"Is Connected","description":"Whether this outcome counts as a live connection in analytics."}},"type":"object","required":["name","color","is_connected"],"title":"VoiceCustomDispositionCreateRequest","description":"Body for creating an org-level custom disposition. Org admin only\n(enforced by voice; see the router docstring above)."},"VoiceCustomDispositionItem":{"properties":{"id":{"type":"integer","title":"Id"},"key":{"type":"string","title":"Key","description":"Stable value to use in filters/writes, e.g. \"custom_42\"."},"name":{"type":"string","title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"color":{"type":"string","title":"Color"},"is_connected":{"type":"boolean","title":"Is Connected"}},"type":"object","required":["id","key","name","color","is_connected"],"title":"VoiceCustomDispositionItem"},"VoiceCustomDispositionUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":40,"minLength":1},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Description"},"color":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Color"},"is_connected":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Connected"}},"type":"object","title":"VoiceCustomDispositionUpdateRequest","description":"Body for editing a custom disposition. Only supplied fields change.\n\n``is_connected`` is locked by voice once any call already references the\ndisposition (changing it would retroactively re-classify historical\ncalls) - forwarded as-is and voice's 409 surfaces to the caller."},"VoiceDispositionListResponse":{"properties":{"system":{"items":{"$ref":"#/components/schemas/VoiceSystemDispositionItem"},"type":"array","title":"System"},"custom":{"items":{"$ref":"#/components/schemas/VoiceCustomDispositionItem"},"type":"array","title":"Custom"},"custom_used":{"type":"integer","title":"Custom Used","default":0},"custom_limit":{"type":"integer","title":"Custom Limit","default":0}},"type":"object","title":"VoiceDispositionListResponse"},"VoiceDraftRequest":{"properties":{"session_id":{"type":"string","format":"uuid","title":"Session Id","description":"The id the new session will have - CALLER-GENERATED, not server-assigned. That is what lets a client open the socket and create the row without a round trip between them. Reusing an id does not create a second session."}},"type":"object","required":["session_id"],"title":"VoiceDraftRequest","description":"Mirror of `VoiceDraftRequest`."},"VoiceInboundTypeRequest":{"properties":{"number":{"type":"string","title":"Number","description":"The number to retype, E.164."},"inbound_type":{"type":"string","enum":["ai","sdr","dialer","work"],"title":"Inbound Type","description":"The answering mode to switch to."}},"type":"object","required":["number","inbound_type"],"title":"VoiceInboundTypeRequest","description":"Retype a number: which system answers its inbound calls.\n\nMirrors `graph8_livekit.schemas.numbers.UpdateNumberInboundType` minus\n`org_id`, which is taken from the key.\n\nNOT a label change. `ai`/`sdr` -> `dialer` TEARS DOWN the LiveKit dispatch\nrule and both SIP trunks and repoints the carrier webhook; the reverse\ncreates them again. A number mid-transition answers nothing."},"VoiceListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"VoiceListPayload","description":"A LIST result from voice, normalised so `items` is always present.\n\nVoice is inconsistent about whether a list comes back bare or under a named\nkey (`collections`, `files`, `routes`, `chats`, ...). Both are preserved:\nthe original key is kept for anyone reading voice's docs, and `items`\nalways holds the same rows so a client can page one way."},"VoiceNumberDeleteRequest":{"properties":{"number":{"type":"string","title":"Number","description":"The number to deregister, E.164."},"provider":{"type":"string","enum":["twilio","telnyx"],"title":"Provider","description":"The carrier to deregister from. Must match how the number was registered, or the provider-side cleanup silently does nothing while the local record still disappears.","default":"twilio"}},"type":"object","required":["number"],"title":"VoiceNumberDeleteRequest","description":"Tear a number's voice registration down.\n\nMirrors the subset of `graph8_livekit.schemas.numbers.Number` that voice's\ndelete handler actually reads (`number`, `provider`); `org_id` comes from\nthe key. The remaining `Number` fields are accepted by voice but never\nread on this path, so publishing them would advertise knobs that do\nnothing."},"VoiceNumberProvisionRequest":{"properties":{"number":{"type":"string","title":"Number","description":"The number to register, E.164. You must already own it."},"provider":{"type":"string","enum":["twilio","telnyx"],"title":"Provider","description":"Which carrier holds the number.","default":"twilio"},"inbound_type":{"anyOf":[{"type":"string","enum":["ai","sdr","dialer","work"]},{"type":"null"}],"title":"Inbound Type","description":"How inbound calls are answered. Ignored when `dialer` or `work` is set - those paths provision no LiveKit trunks at all and the type is forced to `dialer` / `work` respectively.","default":"ai"},"dialer":{"type":"boolean","title":"Dialer","description":"Provision as a dialer number (no LiveKit).","default":false},"work":{"type":"boolean","title":"Work","description":"Provision as someone's personal work phone. Implies `dialer`.","default":false},"assigned_to":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Assigned To","description":"Email of the person this number rings for. REQUIRED in practice for a `work` number: without it no phone-directory row is created, so the receptionist can never route to them by name."}},"type":"object","required":["number"],"title":"VoiceNumberProvisionRequest","description":"Register an already-owned number with the voice platform.\n\nMirrors `graph8_livekit.schemas.numbers.Number` field-for-field EXCEPT\n`org_id`, which is taken from the API key and can never be sent - see the\nrouter docstring.\n\n`number`, not `phone_number`: this is voice's field name, and the proxy\nsends voice's own wire shape rather than inventing a translation layer\nthat would have to be kept in step with it."},"VoicePagination":{"properties":{"total_items":{"type":"integer","title":"Total Items","default":0},"total_pages":{"type":"integer","title":"Total Pages","default":0},"current_page":{"type":"integer","title":"Current Page","default":1},"page_size":{"type":"integer","title":"Page Size","default":50}},"type":"object","title":"VoicePagination","description":"Pagination block returned by the voice list-sessions endpoint.\n\nMirrored verbatim so the field names match what voice already ships\n(``total_items`` / ``total_pages`` / ``current_page`` / ``page_size``).\nKeeping voice's field names here avoids a renaming layer that would\nhave to be updated every time voice extends the block."},"VoicePayload":{"properties":{},"additionalProperties":true,"type":"object","title":"VoicePayload","description":"One voice object - a collection, an agent, a route, a chat.\n\nOpen-shaped: voice adds fields to these bodies on its own release cadence\nand a dropped-or-added key must not be a 500 in this service."},"VoiceQuoteRequest":{"properties":{"voice_id":{"type":"string","format":"uuid","title":"Voice Id","description":"Which voice to price."},"max_input_seconds":{"type":"integer","maximum":1200.0,"minimum":1.0,"title":"Max Input Seconds","description":"Ceiling on spoken input to price for.","default":600},"max_output_characters":{"type":"integer","maximum":60000.0,"minimum":0.0,"title":"Max Output Characters","description":"Ceiling on synthesised output to price for.","default":5000}},"additionalProperties":false,"type":"object","required":["voice_id"],"title":"VoiceQuoteRequest","description":"Mirror of `VoiceQuoteRequest`, including its `extra=\"forbid\"`."},"VoiceSessionRequest":{"properties":{"voice_id":{"type":"string","format":"uuid","title":"Voice Id","description":"Which voice to speak with."},"rate_version":{"type":"string","maxLength":128,"minLength":1,"title":"Rate Version","description":"The rate version the quote was issued against, from `POST /agent/sessions/{session_id}/voice/quote`. The server refuses a stale one rather than charging today's price for yesterday's quote."},"max_credits":{"type":"integer","maximum":9.223372036854776e+18,"minimum":1.0,"title":"Max Credits","description":"HARD CEILING on what this session may spend. Required, with no default: an uncapped voice session is an open-ended charge, and a contract that defaults it would be choosing a spending limit on the customer's behalf."}},"additionalProperties":false,"type":"object","required":["voice_id","rate_version","max_credits"],"title":"VoiceSessionRequest","description":"Mirror of `VoiceSessionRequest`, including its `extra=\"forbid\"`."},"VoiceSystemDispositionItem":{"properties":{"key":{"type":"string","title":"Key"},"is_connected":{"type":"boolean","title":"Is Connected"}},"type":"object","required":["key","is_connected"],"title":"VoiceSystemDispositionItem"},"VoiceTestCallRequest":{"properties":{"from_phone":{"type":"string","minLength":1,"title":"From Phone","description":"One of the organisation's numbers to call from."},"to_phone":{"type":"string","minLength":1,"title":"To Phone","description":"The number to ring. A REAL phone rings."},"agent_id":{"type":"string","minLength":1,"title":"Agent Id","description":"The voice agent that runs the call."},"first_name":{"type":"string","title":"First Name","description":"How the agent addresses the person it rings."},"last_name":{"type":"string","title":"Last Name"},"email":{"type":"string","title":"Email","description":"The test contact's email, as the agent would see it."}},"additionalProperties":false,"type":"object","required":["from_phone","to_phone","agent_id","first_name","last_name","email"],"title":"VoiceTestCallRequest","description":"Place one test call from a voice step. Mirrors `DryRunCallPayload`."},"VoicemailDropRequest":{"properties":{"session_id":{"type":"string","title":"Session Id"},"call_id":{"type":"string","title":"Call Id"}},"type":"object","required":["session_id","call_id"],"title":"VoicemailDropRequest","description":"Mirrors `DialerVoicemailDrop`.\n\nLEAVES A REAL VOICEMAIL on a real person's phone in the rep's cloned\nvoice, then hangs up."},"W8CertifyRequest":{"properties":{"legal_name":{"type":"string","maxLength":200,"minLength":1,"title":"Legal Name"},"country_of_citizenship":{"type":"string","maxLength":2,"minLength":2,"title":"Country Of Citizenship","description":"ISO 3166-1 alpha-2."},"permanent_address":{"type":"string","maxLength":500,"minLength":1,"title":"Permanent Address"},"date_of_birth":{"type":"string","format":"date","title":"Date Of Birth"},"foreign_tax_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Foreign Tax Id"},"certify_checkbox":{"type":"boolean","title":"Certify Checkbox","description":"Must be true - it is the certification itself."},"signature":{"type":"string","maxLength":200,"minLength":1,"title":"Signature","description":"Must match `legal_name`."}},"type":"object","required":["legal_name","country_of_citizenship","permanent_address","date_of_birth","certify_checkbox","signature"],"title":"W8CertifyRequest","description":"W-8BEN certification. Non-US payout rails only.\n\nWRITE-ONLY. The certified payload is encrypted at rest and no published read\nreturns it - `GET /marketplace/me/payout-account/w8-status` answers with a\nboolean and a timestamp and nothing else. Asserted by test.\n\n`signature` must equal `legal_name` (case-insensitively); the app refuses\notherwise with a 422."},"WaterfallConfig":{"properties":{"id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Id"},"name":{"type":"string","title":"Name"},"column_id":{"type":"string","title":"Column Id"},"field_to_enrich":{"type":"string","title":"Field To Enrich"},"data_type":{"type":"string","title":"Data Type","default":"text"},"steps":{"items":{"$ref":"#/components/schemas/WaterfallStep"},"type":"array","title":"Steps"},"is_existing_column":{"type":"boolean","title":"Is Existing Column","default":false},"target_column_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Column Name"},"output_successful_provider":{"type":"boolean","title":"Output Successful Provider","default":false},"hide_provider_columns":{"type":"boolean","title":"Hide Provider Columns","default":true},"skip_existing_values":{"type":"boolean","title":"Skip Existing Values","default":true},"skip_recently_enriched":{"type":"boolean","title":"Skip Recently Enriched","default":true},"validate_emails":{"type":"boolean","title":"Validate Emails","description":"Deprecated: use `email_verification`.","default":false},"email_verification":{"anyOf":[{"$ref":"#/components/schemas/EmailVerificationConfig"},{"type":"null"}]},"list_routing":{"anyOf":[{"$ref":"#/components/schemas/WaterfallListRouting"},{"type":"null"}]},"auto_update":{"type":"boolean","title":"Auto Update","default":true},"only_run_if":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Only Run If","description":"Run condition formula."},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"is_global":{"type":"boolean","title":"Is Global","default":true},"created_by":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created By","description":"Ignored."},"org_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Org Id","description":"Ignored: the key's organisation is used."}},"type":"object","required":["name","column_id","field_to_enrich","steps"],"title":"WaterfallConfig","description":"A complete waterfall definition.\n\n`org_id` and `created_by` are accepted for shape parity with the app and\nIGNORED: the organisation always comes from the API key."},"WaterfallConfigSummary":{"properties":{"column_id":{"type":"string","title":"Column Id"},"name":{"type":"string","title":"Name"},"field_to_enrich":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Field To Enrich"},"data_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Data Type"},"is_global":{"type":"boolean","title":"Is Global","default":false},"is_active":{"type":"boolean","title":"Is Active","default":true},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"step_count":{"type":"integer","title":"Step Count","default":0},"providers":{"items":{"type":"string"},"type":"array","title":"Providers"},"providers_detail":{"items":{"$ref":"#/components/schemas/ProviderStepDetail"},"type":"array","title":"Providers Detail","description":"Per-step credential breakdown (system vs BYOK + readiness) for this pipeline."},"missing_credentials":{"items":{"type":"string"},"type":"array","title":"Missing Credentials","description":"Providers in this pipeline whose step is BYOK but the org has no active key (these steps will be skipped at run time). Empty when everything is runnable."}},"type":"object","required":["column_id","name"],"title":"WaterfallConfigSummary","description":"One saved waterfall pipeline attached to (or global for) a list.\n\n`column_id` is the handle the worker uses to resolve config + store\nenrichment output. `providers` is a de-duplicated list of step providers\nso callers can see at a glance what a pipeline actually runs."},"WaterfallConfigsResponse":{"properties":{"configs":{"items":{"$ref":"#/components/schemas/WaterfallConfigSummary"},"type":"array","title":"Configs"},"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id"},"count":{"type":"integer","title":"Count","default":0}},"type":"object","title":"WaterfallConfigsResponse","description":"Paginated (by list_id filter) collection of waterfall pipeline configs."},"WaterfallListRouting":{"properties":{"enabled":{"type":"boolean","title":"Enabled","default":false},"field_name":{"type":"string","title":"Field Name","default":"email_verified"},"list_mappings":{"additionalProperties":{"type":"integer"},"type":"object","title":"List Mappings","description":"Verification status -> list id."},"copy_columns":{"type":"boolean","title":"Copy Columns","default":false},"routing_columns":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Routing Columns"}},"type":"object","title":"WaterfallListRouting","description":"Route records into lists by their verification result."},"WaterfallStep":{"properties":{"id":{"type":"string","title":"Id"},"provider":{"type":"string","title":"Provider","description":"Provider name, from `GET /enrichment/providers`."},"action":{"type":"string","title":"Action"},"action_display_name":{"type":"string","title":"Action Display Name"},"output_field":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Output Field"},"output_mapping":{"anyOf":[{"additionalProperties":{"type":"string"},"type":"object"},{"type":"null"}],"title":"Output Mapping","description":"Deprecated."},"input_mapping":{"additionalProperties":{"type":"string"},"type":"object","title":"Input Mapping"},"order":{"type":"integer","title":"Order"},"config":{"additionalProperties":true,"type":"object","title":"Config"},"enabled":{"type":"boolean","title":"Enabled","default":true},"is_system_provider":{"type":"boolean","title":"Is System Provider","description":"Use graph8's provider credentials. Those calls are charged.","default":false},"stop_on_success":{"type":"boolean","title":"Stop On Success","default":true},"confidence_threshold":{"type":"number","maximum":1.0,"minimum":0.0,"title":"Confidence Threshold","default":0.0},"max_retries":{"type":"integer","maximum":3.0,"minimum":0.0,"title":"Max Retries","default":0}},"type":"object","required":["id","provider","action","action_display_name","order"],"title":"WaterfallStep","description":"One provider attempt in a waterfall."},"WaterfallStepInput":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id","description":"Step identifier. Auto-generated (`step_<provider>_<uuid8>`) if omitted."},"provider":{"type":"string","title":"Provider","description":"Provider name: graph8, hunter, prospeo, dropcontact, apollo, ..."},"action":{"type":"string","title":"Action","description":"Provider action: lookup_person, find_email, enrich_person, ..."},"action_display_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Action Display Name","description":"Human-readable label shown in UI. Auto-titled from `action` if omitted."},"output_field":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Output Field","description":"Dotted path the worker writes into (e.g. 'contact.work_email')."},"input_mapping":{"additionalProperties":{"type":"string"},"type":"object","title":"Input Mapping","description":"Maps provider input names to graph8 column identifiers (CONTACT_*)."},"output_mapping":{"additionalProperties":{"type":"string"},"type":"object","title":"Output Mapping","description":"Optional output field remap (deprecated — prefer `output_field`)."},"config":{"additionalProperties":true,"type":"object","title":"Config","description":"Provider-specific options (e.g. apollo `reveal_phone_numbers=true`)."},"order":{"type":"integer","minimum":0.0,"title":"Order","description":"0-indexed execution order.","default":0},"enabled":{"type":"boolean","title":"Enabled","default":true},"is_system_provider":{"type":"boolean","title":"Is System Provider","description":"True = use graph8-managed credentials + charge credits. False = use org BYOK.","default":false},"stop_on_success":{"type":"boolean","title":"Stop On Success","default":true},"confidence_threshold":{"type":"number","maximum":1.0,"minimum":0.0,"title":"Confidence Threshold","default":0.0},"max_retries":{"type":"integer","maximum":3.0,"minimum":0.0,"title":"Max Retries","default":0}},"type":"object","required":["provider","action"],"title":"WaterfallStepInput","description":"Single step in a caller-supplied waterfall sequence.\n\nMirrors `WaterfallStepDto` in `enrichment/interfaces/fastapi/waterfall_dtos.py`.\nPersisted verbatim into `enrichment_configs.config.steps[]` so the CF\nworker can resolve provider, action and credentials the same way\nUI-saved pipelines do."},"WebchatListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"WebchatListPayload","description":"An open envelope for a LIST result, so a bare list keeps its shape."},"WebchatPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"WebchatPayload","description":"An open envelope for one webchat object.\n\nOpen because the widget's config grows a field per product decision and a\npinned schema would DROP it. Same choice the desk surface made."},"WebhookCreateRequest":{"properties":{"url":{"type":"string","title":"Url","description":"Target URL for webhook delivery"},"events":{"items":{"type":"string"},"type":"array","title":"Events","description":"Event types to subscribe to"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Human-readable name"},"field_filters":{"anyOf":[{"additionalProperties":{"items":{"type":"string"},"type":"array"},"type":"object"},{"type":"null"}],"title":"Field Filters","description":"Per-object field filter for crm.record.updated: {object_slug: [field_slug]}. When set for an object, an update delivery fires only if a watched field's value changed. Omit or leave empty to fire on any change. Ignored for events other than crm.record.updated."}},"type":"object","required":["url","events"],"title":"WebhookCreateRequest"},"WebhookDeliveryResponse":{"properties":{"id":{"type":"string","title":"Id"},"event":{"type":"string","title":"Event"},"status":{"type":"string","title":"Status"},"attempts":{"type":"integer","title":"Attempts","default":0},"max_attempts":{"type":"integer","title":"Max Attempts","default":3},"response_code":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Response Code"},"error_message":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Error Message"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"completed_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Completed At"}},"type":"object","required":["id","event","status"],"title":"WebhookDeliveryResponse"},"WebhookEventResponse":{"properties":{"event":{"type":"string","title":"Event"},"category":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Category"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"}},"type":"object","required":["event"],"title":"WebhookEventResponse"},"WebhookResponse":{"properties":{"id":{"type":"string","title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"url":{"type":"string","title":"Url"},"events":{"items":{"type":"string"},"type":"array","title":"Events","default":[]},"is_active":{"type":"boolean","title":"Is Active","default":true},"field_filters":{"anyOf":[{"additionalProperties":{"items":{"type":"string"},"type":"array"},"type":"object"},{"type":"null"}],"title":"Field Filters","description":"Per-object field filter for crm.record.updated: {object_slug: [field_slug]}. When set for an object, an update delivery fires only if a watched field's value changed. Omit or leave empty to fire on any change. Ignored for events other than crm.record.updated."},"secret":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Secret","description":"Only returned on create and rotate-secret"},"created_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["id","url"],"title":"WebhookResponse"},"WebhookUpdateRequest":{"properties":{"url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Url","description":"Target URL for webhook delivery"},"events":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Events","description":"Event types to subscribe to"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Human-readable name"},"is_active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Active","description":"Whether the webhook is active"},"field_filters":{"anyOf":[{"additionalProperties":{"items":{"type":"string"},"type":"array"},"type":"object"},{"type":"null"}],"title":"Field Filters","description":"Per-object field filter for crm.record.updated: {object_slug: [field_slug]}. When set for an object, an update delivery fires only if a watched field's value changed. Omit or leave empty to fire on any change. Ignored for events other than crm.record.updated."}},"type":"object","title":"WebhookUpdateRequest"},"WebsiteEditorConnectRequest":{"properties":{"account_id":{"type":"string","title":"Account Id","description":"The hosting provider's account id."},"api_token":{"type":"string","title":"Api Token","description":"An API token for that account. Never returned."},"project_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Project Name","description":"The site project to edit and publish."}},"type":"object","required":["account_id","api_token"],"title":"WebsiteEditorConnectRequest","description":"Connect the org's website hosting account. The token is write-only."},"WebsiteEditorConnection":{"properties":{"connected":{"type":"boolean","title":"Connected"},"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"account_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Id"},"project_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Project Name"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"connected, syncing or error."},"last_synced_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Last Synced At"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated At"}},"type":"object","required":["connected"],"title":"WebsiteEditorConnection","description":"The hosting connection, without its credential."},"WebsiteEditorPageOpsRequest":{"properties":{"ops":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Ops","description":"Ordered edit operations."},"base_version":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Base Version","description":"Your copy's version, for conflict detection."},"save_mode":{"type":"string","enum":["autosave","save"],"title":"Save Mode","default":"autosave"},"instruction":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Instruction","description":"A human-readable note stored on the version."}},"type":"object","required":["ops"],"title":"WebsiteEditorPageOpsRequest","description":"Ordered deterministic edit operations on one page."},"WebsiteEditorPublishRequest":{"properties":{"page_ids":{"anyOf":[{"items":{"type":"string","format":"uuid"},"type":"array"},{"type":"null"}],"title":"Page Ids"}},"type":"object","title":"WebsiteEditorPublishRequest","description":"Which pages to publish. Omit `page_ids` for every page with HTML."},"WebsiteEditorRestoreVersionRequest":{"properties":{"version_num":{"type":"integer","title":"Version Num"}},"type":"object","required":["version_num"],"title":"WebsiteEditorRestoreVersionRequest","description":"Which saved version to restore."},"WebsiteEditorSyncRequest":{"properties":{"project_name":{"type":"string","title":"Project Name","description":"From `GET /website-editor/projects`."},"paths":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Paths","description":"Only these paths. Omit for every page."}},"type":"object","required":["project_name"],"title":"WebsiteEditorSyncRequest","description":"Pull pages from a hosted site project."},"WebsiteEditorUpdateTextRequest":{"properties":{"element_id":{"type":"string","title":"Element Id","description":"The element's `data-g8-id`."},"new_text":{"type":"string","title":"New Text"}},"type":"object","required":["element_id","new_text"],"title":"WebsiteEditorUpdateTextRequest","description":"Set one element's text. No model runs."},"WhatsAppConversationsRequest":{"properties":{"offset":{"type":"integer","minimum":0.0,"title":"Offset","default":0},"limit":{"type":"integer","maximum":100.0,"minimum":1.0,"title":"Limit","default":25},"search":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Search","description":"Name, phone or last-message text."},"unread_only":{"type":"boolean","title":"Unread Only","default":false},"account_ids":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Account Ids","description":"Restrict to these WhatsApp account ids (`wa_...`)."}},"type":"object","title":"WhatsAppConversationsRequest","description":"List filters. Newest activity first; `offset`/`limit` window the list."},"WhatsAppReadRequest":{"properties":{"read":{"type":"boolean","title":"Read","default":true},"account_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Id"}},"type":"object","title":"WhatsAppReadRequest","description":"Mark a conversation read or unread."},"WhatsAppReplyRequest":{"properties":{"text":{"type":"string","maxLength":4096,"minLength":1,"title":"Text","description":"The message. Must not be blank."},"account_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Account Id","description":"Only needed for a chat not yet known to graph8."},"client_message_id":{"anyOf":[{"type":"string","maxLength":188},{"type":"null"}],"title":"Client Message Id","description":"Stable per reply attempt: sent as the idempotency key, so retrying the SAME id never sends twice."}},"type":"object","required":["text"],"title":"WhatsAppReplyRequest","description":"A reply into an existing WhatsApp conversation. THIS SENDS A MESSAGE."},"WithdrawFromSequencesRequest":{"properties":{"sequence_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Id","description":"Sequence to withdraw from. Required unless `remove_all` is true."},"contact_ids":{"items":{"type":"integer"},"type":"array","maxItems":5000,"title":"Contact Ids","description":"Contact primary keys to withdraw (max 5000)."},"target_state":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target State","description":"Terminal state to record: removed | completed | not_interested.","default":"removed"},"remove_all":{"type":"boolean","title":"Remove All","description":"Withdraw from EVERY enrolled sequence. Ignores `sequence_id`.","default":false},"source":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Source","description":"Origin label recorded on the resulting event.","default":"workflow"}},"type":"object","title":"WithdrawFromSequencesRequest","description":"Take contacts OUT of a sequence. They stop receiving its steps.\n\n`remove_all=true` withdraws them from EVERY sequence they are enrolled\nin and ignores `sequence_id`; that is the wider blast radius of the two\nand it is never the default."},"WorkActivityEntry":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id","description":"Activity entry id"},"actor":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Actor","description":"`human`, `agent`, `runner` or `system`"},"category":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Category","description":"message, conversation, approval, execution, workflow, canvas or configuration"},"consequence":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Consequence","description":"requested, changed, approved, completed, failed or recorded"}},"additionalProperties":true,"type":"object","title":"WorkActivityEntry","description":"One entry in the Work activity feed."},"WorkActivityPage":{"properties":{"events":{"items":{"$ref":"#/components/schemas/WorkActivityEntry"},"type":"array","title":"Events","description":"Activity entries, newest first"},"has_more":{"type":"boolean","title":"Has More","description":"Whether older entries remain","default":false},"next_cursor":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Next Cursor","description":"Opaque cursor for the next page"}},"type":"object","title":"WorkActivityPage","description":"One page of the activity feed, scoped to what this credential may read."},"WorkAgentArchived":{"properties":{"agent_id":{"type":"string","title":"Agent Id","description":"The agent that was archived"},"archived":{"type":"boolean","title":"Archived","description":"True once archived","default":true}},"type":"object","required":["agent_id"],"title":"WorkAgentArchived","description":"An archived Work agent."},"WorkAgentCreated":{"properties":{"agent_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent Id","description":"Agent id"},"session_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Session Id","description":"The agent's conversation session id"}},"additionalProperties":true,"type":"object","title":"WorkAgentCreated","description":"A newly created Work agent and its first conversation."},"WorkAgentExecutionIdentities":{"properties":{"items":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Items","description":"Execution identities"},"warnings":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Warnings","description":"Identities that could not be resolved"}},"additionalProperties":true,"type":"object","title":"WorkAgentExecutionIdentities","description":"Identities a Work agent may execute as."},"WorkAgentPolicy":{"properties":{"can_create":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Can Create","description":"May create a private agent"},"can_share_organization":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Can Share Organization","description":"May create an organization-wide agent"}},"additionalProperties":true,"type":"object","title":"WorkAgentPolicy","description":"What this caller may do with Work agents."},"WorkAgentProfile":{"properties":{"agent_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent Id","description":"Agent id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Agent name"},"role":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Role","description":"Role"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Instructions"},"avatar":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Avatar","description":"Avatar glyph"},"visibility":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Visibility","description":"`private` or `organization`"},"owner_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owner Id","description":"Owner identity"},"version":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Version","description":"Profile version; send it back to edit"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At","description":"Last edit time"},"can_edit":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Can Edit","description":"Whether this caller may edit it"}},"additionalProperties":true,"type":"object","title":"WorkAgentProfile","description":"One Work agent profile as the caller may see it."},"WorkAgentProfileEditRequest":{"properties":{"profile":{"$ref":"#/components/schemas/WorkAgentProfileRequest","description":"The full new profile"},"expected_version":{"type":"integer","minimum":1.0,"title":"Expected Version","description":"The `version` you read; a stale one is a 409"}},"additionalProperties":false,"type":"object","required":["profile","expected_version"],"title":"WorkAgentProfileEditRequest","description":"A versioned profile edit. Mirrors ``work.agent_profile_router.AgentProfileEdit``."},"WorkAgentProfilePage":{"properties":{"items":{"items":{"$ref":"#/components/schemas/WorkAgentProfile"},"type":"array","title":"Items","description":"Agents on this page"},"next_cursor":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Next Cursor","description":"Pass as `after` for the next page"}},"type":"object","title":"WorkAgentProfilePage","description":"One page of visible Work agents."},"WorkAgentProfileRequest":{"properties":{"name":{"type":"string","maxLength":100,"minLength":1,"title":"Name","description":"Agent name"},"role":{"type":"string","maxLength":100,"minLength":1,"title":"Role","description":"Role shown beside the name","default":"Assistant"},"description":{"type":"string","maxLength":20000,"minLength":1,"title":"Description","description":"The agent's instructions"},"avatar":{"type":"string","enum":["spark","compass","chart","code","pen","search","shield","bolt"],"title":"Avatar","description":"Avatar glyph","default":"spark"},"visibility":{"type":"string","enum":["private","organization"],"title":"Visibility","description":"`private` to its owner, or shared with the `organization`","default":"private"}},"additionalProperties":false,"type":"object","required":["name","description"],"title":"WorkAgentProfileRequest","description":"A Work agent's profile. Mirrors ``work.agent_profiles.AgentProfileInput``."},"WorkAttachmentLink":{"properties":{"attachment":{"additionalProperties":true,"type":"object","title":"Attachment","description":"Stored attachment metadata"},"url":{"type":"string","title":"Url","description":"Time-limited download URL"},"expires_in":{"type":"integer","title":"Expires In","description":"Seconds until the URL stops working"}},"type":"object","required":["url","expires_in"],"title":"WorkAttachmentLink","description":"A short-lived download link for one attachment."},"WorkAvailableChannel":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id","description":"Channel id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Channel slug"},"displayName":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Displayname","description":"Human-readable name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Present for `open` channels only"},"memberCount":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Membercount","description":"Present for `open` channels only"},"visibility":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Visibility","description":"`open` or `private`"}},"additionalProperties":true,"type":"object","title":"WorkAvailableChannel","description":"A channel of this organization the caller is not currently part of.\n\nAn `open` channel carries its description and member count; a `private` one\nanswers with identity only, so nothing about the room itself leaks."},"WorkAvailableChannelList":{"properties":{"channels":{"items":{"$ref":"#/components/schemas/WorkAvailableChannel"},"type":"array","title":"Channels","description":"Channels the caller is not part of"}},"type":"object","title":"WorkAvailableChannelList","description":"The organization's channels the caller is not in."},"WorkCanvas":{"properties":{"channelId":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Channelid","description":"Channel the canvas belongs to"},"content":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Content","description":"Canvas content"},"revisionId":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Revisionid","description":"Current revision id"}},"additionalProperties":true,"type":"object","title":"WorkCanvas","description":"One channel's Canvas document."},"WorkCanvasSaveRequest":{"properties":{"content":{"type":"string","maxLength":100000,"title":"Content"},"baseRevisionId":{"anyOf":[{"type":"string","maxLength":128},{"type":"null"}],"title":"Baserevisionid"}},"additionalProperties":false,"type":"object","required":["content"],"title":"WorkCanvasSaveRequest","description":"One channel canvas replacement, by CONTENT.\n\nThe channel is named by the path, the author by the session, the\nidempotency key by the header — this body carries only the markdown. An\nempty string is a legal canvas (it clears the document); the 100k ceiling\nis the gateway's own. Server-owned fields are refused by name rather than\nswallowed by `extra=\"forbid\"`, matching every other Work write DTO: a\nclient that believes it is choosing the author must be told it is not."},"WorkCertificateIssueRequest":{"properties":{"hiring_id":{"type":"string","title":"Hiring Id","description":"Your own signed active/completed engagement (UUID)."}},"type":"object","required":["hiring_id"],"title":"WorkCertificateIssueRequest","description":"Issue a verifiable certificate for one of your own signed engagements."},"WorkChannel":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id","description":"Channel id (uuid5 of `{org}:{name}` — the room address)"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Slug, unique per organization. Renaming the display name never moves the room."},"displayName":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Displayname","description":"Human-readable name shown in the sidebar"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Channel description"},"visibility":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Visibility","description":"`open` (self-serve joinable) or `private` (invite only)"},"kind":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Kind","description":"`stream` or `forum`"},"memberUserIds":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Memberuserids","description":"Seated member identities"},"participantAgentIds":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Participantagentids","description":"Seated agent ids"},"system":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"System","description":"True for a built-in channel (`#work`, `#signals`)"},"archivedAt":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Archivedat","description":"When the channel was archived, if it is"},"createdBy":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Createdby","description":"Identity that created the channel"},"createdAt":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Createdat","description":"Creation timestamp"}},"additionalProperties":true,"type":"object","title":"WorkChannel","description":"One Work channel as the room stores it."},"WorkChannelCreateRequest":{"properties":{"name":{"type":"string","maxLength":255,"minLength":1,"title":"Name"},"displayName":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Displayname"},"description":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Description"},"visibility":{"type":"string","enum":["open","private"],"title":"Visibility","default":"open"},"kind":{"type":"string","enum":["stream","forum"],"title":"Kind","default":"stream"},"memberUserIds":{"items":{"type":"string"},"type":"array","maxItems":200,"title":"Memberuserids"},"participantAgentIds":{"items":{"type":"string"},"type":"array","maxItems":16,"title":"Participantagentids"},"templateId":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Templateid","description":"One of `work/channel_templates.py`'s ids. Seats its specialists and seeds its Canvas."},"ttlSeconds":{"anyOf":[{"type":"integer","maximum":2147483647.0,"exclusiveMinimum":0.0},{"type":"null"}],"title":"Ttlseconds","description":"A Temporary channel's lifetime in seconds; absent means Permanent."}},"additionalProperties":false,"type":"object","required":["name"],"title":"WorkChannelCreateRequest","description":"One channel a person is creating.\n\nCarries what the channel IS and who is seated in it — never who is creating\nit. The creator, the organization and the signing identity all come from the\nauthenticated session in `work/router.py`, and `Idempotency-Key` comes from\nthe header. `SERVER_OWNED_MESSAGE_FIELDS` is reused verbatim for the refusal\nbecause the danger is identical: `create_work_event` turns whatever\n`actor_id`/`org_id` it is handed into the signing key AND the `g8_actor` /\n`g8_org` tags."},"WorkChannelDeleteRequest":{"properties":{"confirmationName":{"type":"string","maxLength":255,"minLength":1,"title":"Confirmationname"}},"additionalProperties":false,"type":"object","required":["confirmationName"],"title":"WorkChannelDeleteRequest"},"WorkChannelIcon":{"properties":{"type":{"type":"string","enum":["glyph","emoji","image"],"title":"Type"},"glyph":{"anyOf":[{"type":"string","pattern":"^[a-z0-9-]{1,40}$"},{"type":"null"}],"title":"Glyph"},"emoji":{"anyOf":[{"type":"string","maxLength":16,"minLength":1},{"type":"null"}],"title":"Emoji"},"color":{"anyOf":[{"type":"string","pattern":"^[a-z0-9-]{1,32}$"},{"type":"null"}],"title":"Color"},"attachmentId":{"anyOf":[{"type":"string","pattern":"^[A-Za-z0-9-]{1,64}$"},{"type":"null"}],"title":"Attachmentid"}},"additionalProperties":false,"type":"object","required":["type"],"title":"WorkChannelIcon","description":"A channel's icon: a glyph on a color, an emoji, or an uploaded image.\n\n`glyph` and `color` are ids from the client's curated sets, never raw CSS\nor SVG, so nothing a member stores can inject markup or styles into\nanother member's sidebar. An image is a Work attachment id, never a URL:\nreadability is re-checked on every read (`readable_attachment_ids`)."},"WorkChannelList":{"properties":{"channels":{"items":{"$ref":"#/components/schemas/WorkChannel"},"type":"array","title":"Channels","description":"Channels visible to the caller"}},"type":"object","title":"WorkChannelList","description":"The channels this credential may read."},"WorkChannelPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"WorkChannelPayload","description":"A Work channel, chat, output, task, decision or activity document, as the app returns it."},"WorkChannelPurposeRequest":{"properties":{"purpose":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Purpose"}},"additionalProperties":false,"type":"object","required":["purpose"],"title":"WorkChannelPurposeRequest","description":"The purpose one channel is being given, or `null` to clear it.\n\nRequired-but-nullable on purpose: `{}` would be ambiguous between \"clear it\"\nand \"I forgot the field\", and this operation reassigns state on channels the\ncaller did not name, so it may not act on an ambiguity."},"WorkChannelSettingsRequest":{"properties":{"displayName":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Displayname"},"description":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Description"},"visibility":{"anyOf":[{"type":"string","enum":["open","private"]},{"type":"null"}],"title":"Visibility"},"memberUserIds":{"items":{"type":"string"},"type":"array","maxItems":100,"title":"Memberuserids"},"participantAgentIds":{"items":{"type":"string"},"type":"array","maxItems":32,"title":"Participantagentids"},"agentResponsePolicy":{"anyOf":[{"type":"string","enum":["mention_required","proactive"]},{"type":"null"}],"title":"Agentresponsepolicy"},"confirmAgentAccess":{"type":"boolean","title":"Confirmagentaccess","default":false},"archived":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Archived"},"icon":{"anyOf":[{"$ref":"#/components/schemas/WorkChannelIcon"},{"type":"null"}]}},"additionalProperties":false,"type":"object","title":"WorkChannelSettingsRequest","description":"The fields of one channel a person is changing.\n\n**Field PRESENCE is the contract, not field value.** An omitted field keeps\nwhatever the channel already has; a field present with `null` clears it\nwhere clearing is meaningful (`description`) and is refused where it is not.\nThat is the port of the gateway's `Object.hasOwn(input, …)` checks, and it\nis why `provided_fields` — not the values — is what the router hands the\nservice."},"WorkChannelTaskCreateBody":{"properties":{"title":{"type":"string","maxLength":500,"minLength":1,"title":"Title"},"ownerUserId":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Owneruserid","description":"The ASSIGNEE's user id (the caller when omitted)."},"dueAt":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Dueat","description":"A calendar day `YYYY-MM-DD`; only the date is kept."},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description","description":"Plain text."}},"additionalProperties":false,"type":"object","required":["title"],"title":"WorkChannelTaskCreateBody","description":"A task a person gives to a person from the channel. Names no identity and no channel."},"WorkChannelWriteResult":{"properties":{"channel":{"anyOf":[{"$ref":"#/components/schemas/WorkChannel"},{"type":"null"}],"description":"The channel as stored after the write"},"duplicate":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Duplicate","description":"True when an Idempotency-Key replay returned the original result"},"canvasSeeded":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Canvasseeded","description":"Present when `templateId` seeded a Canvas"}},"additionalProperties":true,"type":"object","title":"WorkChannelWriteResult","description":"The result of one channel write, with its idempotent-replay marker."},"WorkChatConvertBody":{"properties":{"name":{"type":"string","maxLength":255,"minLength":1,"title":"Name"},"displayName":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Displayname"}},"additionalProperties":false,"type":"object","required":["name"],"title":"WorkChatConvertBody","description":"The channel a chat becomes. The name is normalised like a new channel's name."},"WorkChatCreateBody":{"properties":{"title":{"anyOf":[{"type":"string","maxLength":4000},{"type":"null"}],"title":"Title","description":"What the chat is about. Trimmed to one sidebar line."},"initialMessage":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Initialmessage","description":"The chat's first message, posted in the same request: the body of `POST /work/messages` without `channel` or a thread. THIS STARTS THE CHIEF OF STAFF'S TURN, which spends credits."},"subject":{"anyOf":[{"$ref":"#/components/schemas/WorkChatSubjectBody"},{"type":"null"}],"description":"The record this chat is about; the person's live chat about it is reopened."}},"additionalProperties":false,"type":"object","title":"WorkChatCreateBody","description":"A new chat. It names nothing but an optional title, a first message and a subject."},"WorkChatSubjectBody":{"properties":{"kind":{"type":"string","enum":["deal","company","desk_card"],"title":"Kind"},"id":{"type":"string","maxLength":64,"minLength":1,"title":"Id"}},"additionalProperties":false,"type":"object","required":["kind","id"],"title":"WorkChatSubjectBody","description":"The record a chat is about."},"WorkChatUpdateBody":{"properties":{"title":{"anyOf":[{"type":"string","maxLength":1000},{"type":"null"}],"title":"Title","description":"The chat's new name."},"archived":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Archived","description":"True puts the chat in the caller's Archive; false brings it back."}},"additionalProperties":false,"type":"object","title":"WorkChatUpdateBody","description":"A rename and/or an archive change. A field left out is left alone; at least one is required."},"WorkCustomEmojiRequest":{"properties":{"shortcode":{"type":"string","maxLength":32,"minLength":2,"title":"Shortcode"},"url":{"type":"string","maxLength":2048,"minLength":1,"title":"Url"}},"additionalProperties":false,"type":"object","required":["shortcode","url"],"title":"WorkCustomEmojiRequest","description":"One organization-wide custom emoji.\n\nThe URL is constrained to `https:` on purpose and refused rather than\ncoerced. A custom emoji is rendered by every member's browser in every\nchannel that uses it, so an `http:` or `javascript:` URL here is not a\nformatting problem — it is a stored payload with an audience."},"WorkCustomEmojiResult":{"properties":{"event":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Event","description":"The room event the write appended"},"customEmojis":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Customemojis","description":"Every custom emoji the organization now has"},"duplicate":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Duplicate","description":"True when an Idempotency-Key replay returned the original result"}},"additionalProperties":true,"type":"object","title":"WorkCustomEmojiResult","description":"The organization's custom emoji after one registration."},"WorkDailyBriefSettings":{"properties":{"settings":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Settings","description":"The stored schedule"},"status":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Status","description":"Delivery status (`latestBrief`, `lastBriefDate`, `nextDueAt`, `reason`). Returned on the read only; null on the write"}},"additionalProperties":true,"type":"object","title":"WorkDailyBriefSettings","description":"This principal's daily-brief schedule and, on a read, its delivery status."},"WorkDailyBriefSettingsRequest":{"properties":{"enabled":{"type":"boolean","title":"Enabled","default":false},"timezone":{"type":"string","maxLength":100,"minLength":1,"title":"Timezone"},"weekdays":{"anyOf":[{"items":{"type":"integer"},"type":"array","maxItems":7},{"type":"null"}],"title":"Weekdays"},"localTime":{"anyOf":[{"type":"string","maxLength":5},{"type":"null"}],"title":"Localtime"}},"additionalProperties":false,"type":"object","required":["timezone"],"title":"WorkDailyBriefSettingsRequest","description":"When this person wants their daily brief.\n\nThe timezone is the one field that is REFUSED rather than defaulted. A\nbrief is a scheduled send, and an unrecognised zone has no defensible\nfallback: guessing UTC delivers somebody's morning brief at midnight,\nsilently, forever. `weekdays` and `localTime` do have a defensible default\n(weekdays at 08:00) and take it, which is the gateway's split too."},"WorkDocumentBodyBody":{"properties":{"content":{"type":"string","maxLength":500000,"title":"Content"},"expectedUpdatedAt":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Expectedupdatedat","description":"The `updated_at` the editor loaded. The save fails with 409 if the document has moved on."}},"additionalProperties":false,"type":"object","required":["content"],"title":"WorkDocumentBodyBody","description":"A document's new body: Markdown, replaced whole."},"WorkDocumentCreateBody":{"properties":{"templateId":{"type":"string","maxLength":40,"minLength":1,"title":"Templateid"},"title":{"anyOf":[{"type":"string","maxLength":400},{"type":"null"}],"title":"Title"}},"additionalProperties":false,"type":"object","required":["templateId"],"title":"WorkDocumentCreateBody","description":"Create a document from one of the server's templates."},"WorkEvent":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id","description":"Event id"},"kind":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Kind","description":"Event kind number"},"created_at":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Created At","description":"Event creation time"}},"additionalProperties":true,"type":"object","title":"WorkEvent","description":"One signed Work event from the conversation ledger."},"WorkEventPage":{"properties":{"conversation_id":{"type":"string","title":"Conversation Id","description":"The conversation these events belong to"},"events":{"items":{"$ref":"#/components/schemas/WorkEvent"},"type":"array","title":"Events","description":"Events the caller may read"},"has_more":{"type":"boolean","title":"Has More","description":"Whether older stored rows remain","default":false},"next_cursor":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Next Cursor","description":"Opaque cursor for the next page"},"cleared_behind":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Cleared Behind","description":"True when the caller's own clear watermark hides everything older"}},"type":"object","required":["conversation_id"],"title":"WorkEventPage","description":"One page of a conversation's chat events, newest first."},"WorkInboxDisposition":{"properties":{"disposition":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Disposition","description":"The disposition as stored"},"duplicate":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Duplicate","description":"True when an Idempotency-Key replay returned the original result"}},"additionalProperties":true,"type":"object","title":"WorkInboxDisposition","description":"One conversation's Inbox state after a write."},"WorkInboxDispositionRequest":{"properties":{"conversationKey":{"type":"string","maxLength":512,"minLength":1,"title":"Conversationkey"},"state":{"type":"string","enum":["active","snoozed","archived"],"title":"State"},"latestActivityAt":{"type":"integer","minimum":0.0,"title":"Latestactivityat"},"channel":{"type":"string","maxLength":255,"minLength":1,"title":"Channel"},"rootId":{"type":"string","maxLength":128,"minLength":1,"title":"Rootid"},"snoozedUntil":{"anyOf":[{"type":"string","maxLength":64},{"type":"null"}],"title":"Snoozeduntil"}},"additionalProperties":false,"type":"object","required":["conversationKey","state","latestActivityAt","channel","rootId"],"title":"WorkInboxDispositionRequest","description":"One conversation moving between the Inbox's three states.\n\n`latest_activity_at` is the conversation boundary the decision was made at,\nnot a timestamp of the decision: a newer inbound message must re-activate a\nsnoozed or archived conversation without erasing the record that somebody\nonce set it aside. That is why the state is stored per conversation rather\nthan as a flag on the conversation itself."},"WorkInboxDispositions":{"properties":{"dispositions":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Dispositions","description":"Conversation key -> `active`, `snoozed` or `archived`"}},"additionalProperties":true,"type":"object","title":"WorkInboxDispositions","description":"This principal's Inbox states, keyed by conversation."},"WorkItem":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id","description":"Work item id"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title","description":"What the work is"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"Lifecycle status"},"ownerUserId":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Owneruserid","description":"Identity the item is assigned to"},"priority":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Priority","description":"Priority band"},"dueAt":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Dueat","description":"Due date, when one is set"}},"additionalProperties":true,"type":"object","title":"WorkItem","description":"One unit of agent work on the All Work board."},"WorkItemList":{"properties":{"work_items":{"items":{"$ref":"#/components/schemas/WorkItem"},"type":"array","title":"Work Items","description":"Work items visible to the caller"}},"type":"object","title":"WorkItemList","description":"A page of work items."},"WorkMemoryEditRequest":{"properties":{"scope":{"type":"string","enum":["personal","agent","team"],"title":"Scope","description":"`personal`, `agent` or `team`","default":"personal"},"agent_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Agent Id","description":"Required for, and only for, `agent` scope"},"topic":{"type":"string","enum":["profile","goals","decisions","feedback","corrections","entities"],"title":"Topic","description":"The topic to replace"},"content":{"type":"string","maxLength":49152,"title":"Content","description":"The new content"},"expected_revision":{"anyOf":[{"type":"string","pattern":"^[a-f0-9]{64}$"},{"type":"null"}],"title":"Expected Revision","description":"The `revision` you read, or null when the topic is new"}},"additionalProperties":false,"type":"object","required":["topic","content","expected_revision"],"title":"WorkMemoryEditRequest","description":"Replace one memory topic. Mirrors ``work.memory_router.MemoryEdit``."},"WorkMemoryMoveRequest":{"properties":{"source":{"$ref":"#/components/schemas/WorkMemoryScope","description":"Where the topic is now"},"destination":{"$ref":"#/components/schemas/WorkMemoryScope","description":"Where it should go"},"topic":{"type":"string","enum":["profile","goals","decisions","feedback","corrections","entities"],"title":"Topic","description":"The topic to move"},"source_revision":{"type":"string","pattern":"^[a-f0-9]{64}$","title":"Source Revision","description":"The source topic's current revision"},"destination_revision":{"anyOf":[{"type":"string","pattern":"^[a-f0-9]{64}$"},{"type":"null"}],"title":"Destination Revision","description":"The destination topic's revision, or null when it is empty"}},"additionalProperties":false,"type":"object","required":["source","destination","topic","source_revision","destination_revision"],"title":"WorkMemoryMoveRequest","description":"Move one topic between scopes. Mirrors ``work.memory_router.MemoryMove``."},"WorkMemoryNote":{"properties":{"topic":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Topic","description":"Topic"},"content":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Content","description":"Content"},"size_bytes":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Size Bytes","description":"Stored size"},"updated_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Updated At","description":"Last write time"},"revision":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Revision","description":"Revision; send it back to edit or move"}},"additionalProperties":true,"type":"object","title":"WorkMemoryNote","description":"One memory topic."},"WorkMemoryPage":{"properties":{"scope":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Scope","description":"The scope read"},"agent_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agent Id","description":"The agent, for `agent` scope"},"entries":{"anyOf":[{"items":{"$ref":"#/components/schemas/WorkMemoryNote"},"type":"array"},{"type":"null"}],"title":"Entries","description":"The topics"},"can_edit":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Can Edit","description":"Whether this caller may edit this scope"}},"additionalProperties":true,"type":"object","title":"WorkMemoryPage","description":"Every topic in one memory scope."},"WorkMemoryScope":{"properties":{"scope":{"type":"string","enum":["personal","agent","team"],"title":"Scope","description":"`personal`, `agent` or `team`","default":"personal"},"agent_id":{"anyOf":[{"type":"string","format":"uuid"},{"type":"null"}],"title":"Agent Id","description":"Required for, and only for, `agent` scope"}},"additionalProperties":false,"type":"object","title":"WorkMemoryScope","description":"Which memory to act on. Mirrors ``work.memory.MemorySelection``."},"WorkMessage":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id","description":"Message id"},"channel":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Channel","description":"Conversation address — a channel NAME or a direct-message id"},"document":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Document","description":"Rich-text document, normalized server-side"},"text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Text","description":"Plain-text projection of the document"},"author":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Author","description":"Resolved author — always the authenticated principal, never a request field"},"createdAt":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Createdat","description":"Creation timestamp"}},"additionalProperties":true,"type":"object","title":"WorkMessage","description":"One stored Work message."},"WorkMessageCreateRequest":{"properties":{"channel":{"type":"string","maxLength":255,"minLength":1,"title":"Channel"},"message":{"anyOf":[{"type":"string","maxLength":12000},{"type":"null"}],"title":"Message"},"document":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Document"},"parentMessageId":{"anyOf":[{"type":"string","maxLength":128},{"type":"null"}],"title":"Parentmessageid"},"rootMessageId":{"anyOf":[{"type":"string","maxLength":128},{"type":"null"}],"title":"Rootmessageid"},"projectId":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Projectid"},"mentionUserIds":{"items":{"type":"string"},"type":"array","maxItems":64,"title":"Mentionuserids"},"mentionAgentIds":{"items":{"type":"string"},"type":"array","maxItems":16,"title":"Mentionagentids"},"attachmentIds":{"items":{"type":"string"},"type":"array","maxItems":20,"title":"Attachmentids"}},"additionalProperties":false,"type":"object","required":["channel"],"title":"WorkMessageCreateRequest","description":"One message a person is sending into a Work channel.\n\nCarries what is being said and where — never who is saying it. The author,\nthe organization and the signing identity all come from the authenticated\nsession in `work/router.py`; `Idempotency-Key` comes from the header."},"WorkMessageEditRequest":{"properties":{"text":{"anyOf":[{"type":"string","maxLength":12000},{"type":"null"}],"title":"Text"},"document":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Document"},"expected_revision":{"type":"integer","minimum":1.0,"title":"Expected Revision","default":1}},"additionalProperties":false,"type":"object","title":"WorkMessageEditRequest","description":"New words for a message the caller wrote. Never who wrote it, or where."},"WorkMessageForwardRequest":{"properties":{"channel":{"type":"string","maxLength":255,"minLength":1,"title":"Channel"}},"additionalProperties":false,"type":"object","required":["channel"],"title":"WorkMessageForwardRequest"},"WorkMessagePage":{"properties":{"conversation_id":{"type":"string","title":"Conversation Id","description":"The conversation these messages belong to"},"messages":{"items":{"$ref":"#/components/schemas/WorkMessage"},"type":"array","title":"Messages","description":"Messages the caller may read"},"has_more":{"type":"boolean","title":"Has More","description":"Whether older stored rows remain","default":false},"next_cursor":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Next Cursor","description":"Opaque cursor for the next page"},"cleared_behind":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Cleared Behind","description":"True when the caller's own clear watermark hides everything older"}},"type":"object","required":["conversation_id"],"title":"WorkMessagePage","description":"One page of a conversation's messages, newest first."},"WorkMessageReactionRequest":{"properties":{"emoji":{"type":"string","maxLength":32,"minLength":1,"title":"Emoji"},"active":{"type":"boolean","title":"Active"}},"additionalProperties":false,"type":"object","required":["emoji","active"],"title":"WorkMessageReactionRequest"},"WorkOutputRenameBody":{"properties":{"title":{"type":"string","maxLength":400,"minLength":1,"title":"Title"}},"additionalProperties":false,"type":"object","required":["title"],"title":"WorkOutputRenameBody","description":"A new title for an output (and its document)."},"WorkOversight":{"properties":{},"additionalProperties":true,"type":"object","title":"WorkOversight","description":"What needs a person: approvals, blocked work and unattended fixes.\n\nEach group carries its own state, so one failed read never blanks the others\nand an empty list always says which of \"nothing here\", \"we could not find\nout\" and \"nothing is recorded for this workspace\" it means."},"WorkProject":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id","description":"Project id, minted server-side"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Project name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Project description; null when cleared"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"`active`, `paused`, `completed` or `archived`"},"channel":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Channel","description":"Channel the project belongs to"},"createdBy":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Createdby","description":"Ownership identity of whoever created it"}},"additionalProperties":true,"type":"object","title":"WorkProject","description":"One project: a named unit of work attached to a channel."},"WorkProjectCreateRequest":{"properties":{"channel":{"type":"string","maxLength":255,"minLength":1,"title":"Channel"},"name":{"type":"string","maxLength":500,"minLength":1,"title":"Name"},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description"},"status":{"type":"string","enum":["active","paused","completed","archived"],"title":"Status","default":"active"}},"additionalProperties":false,"type":"object","required":["channel","name"],"title":"WorkProjectCreateRequest","description":"One project a person is creating, in one channel.\n\n`channel` is the channel NAME — a project belongs to a room, and the room\ndecides who may create one. The identifier is minted server-side and the\ncreator comes from the session; `SERVER_OWNED_MESSAGE_FIELDS` refuses a\nbody that tries to assert either, by name rather than by `extra=\"forbid\"`."},"WorkProjectDeleteRequest":{"properties":{"reason":{"type":"string","maxLength":500,"minLength":1,"title":"Reason","default":"user_requested"}},"type":"object","title":"WorkProjectDeleteRequest","description":"Auditable project tombstone input."},"WorkProjectDeleted":{"properties":{"project_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Project Id","description":"The project that was tombstoned"},"deleted":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Deleted","description":"True once the tombstone is in place"},"deleted_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Deleted At","description":"When the tombstone was written"},"messages_preserved":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Messages Preserved","description":"Messages KEPT: deleting a project does not delete its conversation"},"action_receipts_preserved":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Action Receipts Preserved","description":"Action receipts KEPT, for the same reason"}},"additionalProperties":true,"type":"object","title":"WorkProjectDeleted","description":"A project tombstone readback. What survives is named, not implied."},"WorkProjectUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string","maxLength":2000},{"type":"null"}],"title":"Description"},"status":{"anyOf":[{"type":"string","enum":["active","paused","completed","archived"]},{"type":"null"}],"title":"Status"}},"additionalProperties":false,"type":"object","title":"WorkProjectUpdateRequest","description":"One project being changed. Field PRESENCE is the contract.\n\n`channel` is absent on purpose: a project's channel is where its messages\nand receipts already point, so moving one would strand them. Renaming,\nre-describing and moving its status are what this accepts."},"WorkProjectWriteResult":{"properties":{"project":{"anyOf":[{"$ref":"#/components/schemas/WorkProject"},{"type":"null"}],"description":"The project as stored after the write"},"duplicate":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Duplicate","description":"True when an Idempotency-Key replay returned the original result rather than writing again"},"compatibilityEventId":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Compatibilityeventid","description":"Id of the room event the write appended"}},"additionalProperties":true,"type":"object","title":"WorkProjectWriteResult","description":"The result of one project write, with its idempotent-replay marker."},"WorkPulseNote":{"properties":{"event":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Event","description":"The room event carrying the note"},"duplicate":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Duplicate","description":"True when an Idempotency-Key replay returned the original result"}},"additionalProperties":true,"type":"object","title":"WorkPulseNote","description":"One posted pulse update."},"WorkPulseNoteRequest":{"properties":{"content":{"type":"string","maxLength":2000,"minLength":1,"title":"Content"},"replyToEventId":{"anyOf":[{"type":"string","maxLength":128},{"type":"null"}],"title":"Replytoeventid"}},"additionalProperties":false,"type":"object","required":["content"],"title":"WorkPulseNoteRequest","description":"One pulse update — the room's org-wide, channel-less status note."},"WorkPulseReaction":{"properties":{"event":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Event","description":"The room event, or null when taking back an upvote nobody had left nothing to write"},"reacted":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Reacted","description":"The state that now stands"},"duplicate":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Duplicate","description":"True when the request asked for the state already stored"}},"additionalProperties":true,"type":"object","title":"WorkPulseReaction","description":"The upvote that now stands on a pulse note."},"WorkPulseReactionRequest":{"properties":{"reacted":{"type":"boolean","title":"Reacted"}},"additionalProperties":false,"type":"object","required":["reacted"],"title":"WorkPulseReactionRequest","description":"Upvote one pulse note, or take the upvote back.\n\n`reacted` is the DESIRED state, not a toggle. A toggle would make the\noutcome depend on what the client believed the current state was, which is\nexactly the assumption two open tabs break; asserting the target state lets\nthe server short-circuit a request that asks for the state it is already in."},"WorkReadMarkerRequest":{"properties":{"conversationKey":{"type":"string","maxLength":512,"minLength":1,"title":"Conversationkey"},"lastReadAt":{"type":"integer","minimum":0.0,"title":"Lastreadat"},"lastReadId":{"anyOf":[{"type":"string","maxLength":128,"minLength":1},{"type":"null"}],"title":"Lastreadid"},"channel":{"type":"string","maxLength":255,"minLength":1,"title":"Channel"},"rootId":{"type":"string","maxLength":128,"minLength":1,"title":"Rootid"}},"additionalProperties":false,"type":"object","required":["conversationKey","lastReadAt","channel","rootId"],"title":"WorkReadMarkerRequest","description":"How far this person has read ONE conversation.\n\n`last_read_at` is the conversation's `latestAt` boundary the reader was\nshown, in unix seconds — the same clock `WorkInboxDispositionRequest`\nkeeps in `latest_activity_at` — not the instant they looked. A newer\ninbound message therefore lights the badge again on its own: the\ncomparison is `latestAt > lastReadAt`, and nothing has to un-mark anything.\n\nSeconds are not a total order: `post_message` truncates event timestamps\nto whole seconds, so a message that lands in the SAME second as the one\nthe reader saw would compare equal and pass as read. `last_read_id` — the\nid of the newest message the reader was shown — is the tiebreaker: at an\nequal second, only a matching id counts as read (Codex on #16589)."},"WorkReadMarkers":{"properties":{"markers":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Markers","description":"Conversation key -> the point this principal has read to"}},"additionalProperties":true,"type":"object","title":"WorkReadMarkers","description":"This principal's read markers, keyed by conversation."},"WorkReadMarkersRequest":{"properties":{"markers":{"items":{"$ref":"#/components/schemas/WorkReadMarkerRequest"},"type":"array","maxItems":200,"minItems":1,"title":"Markers"}},"additionalProperties":false,"type":"object","required":["markers"],"title":"WorkReadMarkersRequest","description":"A batch of read markers — one request per room opened, not per thread.\n\nOpening a channel with four waiting threads reads all four at once; four\nround trips racing one read-modify-write of the same JSONB value is the\nwrite pattern the org lock exists to serialize, so the batch is the unit.\nBounded so a runaway client cannot hand the server a map to merge."},"WorkRoom":{"properties":{"room":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Room","description":"Channels, direct messages, messages, events and per-viewer state the caller may read"},"counts":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Counts","description":"Per-collection counts of what the caller can see"},"truncation":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Truncation","description":"What was left out of the bounded read, and the cursors to resume from"},"members":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Members","description":"Organization member directory, for turning an actor id into a name"},"agents":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Agents","description":"Agent roster available in this workspace"}},"additionalProperties":true,"type":"object","title":"WorkRoom","description":"The canonical Work room, scoped and bounded for whoever asked for it."},"WorkRoutine":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id","description":"Routine id"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title","description":"Routine title"},"instruction":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Instruction","description":"What the agent is asked to do each run"},"agentId":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agentid","description":"Agent that runs the routine"},"deliveryConversationId":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Deliveryconversationid","description":"Conversation the routine posts into"},"enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Enabled","description":"Whether the routine is active"},"triggerKind":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Triggerkind","description":"`schedule` or `event`"},"weekdays":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Weekdays","description":"Schedule weekdays (0-6), for `schedule` routines"},"localTime":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Localtime","description":"Local run time, for `schedule` routines"},"timezone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Timezone","description":"IANA timezone the local time is read in"},"lastRunAt":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Lastrunat","description":"When the routine last ran"},"lastStatus":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Laststatus","description":"How the last run ended"}},"additionalProperties":true,"type":"object","title":"WorkRoutine","description":"One scheduled or event-triggered Work routine."},"WorkRoutineCreateRequest":{"properties":{"agentId":{"type":"string","title":"Agentid","description":"Agent that runs the routine"},"title":{"type":"string","title":"Title","description":"What the routine is called"},"instruction":{"type":"string","title":"Instruction","description":"What the agent is asked to do each run"},"deliveryConversationId":{"type":"string","title":"Deliveryconversationid","description":"Conversation the routine posts into; must be readable by the caller"},"weekdays":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Weekdays","description":"Days to run on (0-6), for `schedule` routines"},"localTime":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Localtime","description":"Local run time `HH:MM`, for `schedule` routines"},"timezone":{"type":"string","title":"Timezone","description":"IANA timezone the local time is read in","default":"UTC"},"enabled":{"type":"boolean","title":"Enabled","description":"Whether the routine starts active","default":true},"triggerKind":{"type":"string","title":"Triggerkind","description":"`schedule` or `event`","default":"schedule"},"trigger":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Trigger","description":"Trigger config, for `event` routines"},"eventPolicy":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Eventpolicy","description":"Optional event-handling policy"}},"additionalProperties":false,"type":"object","required":["agentId","title","instruction","deliveryConversationId"],"title":"WorkRoutineCreateRequest","description":"One routine to create. Identity is never expressible here."},"WorkRoutineDeleted":{"properties":{"id":{"type":"string","title":"Id","description":"The routine that was deleted"},"deleted":{"type":"boolean","title":"Deleted","description":"Always true; the operation is idempotent","default":true}},"type":"object","required":["id"],"title":"WorkRoutineDeleted","description":"Confirmation that one routine is gone."},"WorkRoutineEnvelope":{"properties":{"routine":{"$ref":"#/components/schemas/WorkRoutine","description":"The routine as stored after the write"}},"type":"object","required":["routine"],"title":"WorkRoutineEnvelope","description":"One routine, as the create and update operations return it."},"WorkRoutineList":{"properties":{"routines":{"items":{"$ref":"#/components/schemas/WorkRoutine"},"type":"array","title":"Routines","description":"Routines, with recent event activity folded in"}},"type":"object","title":"WorkRoutineList","description":"Every routine in this organization's workspace."},"WorkRoutinePatchRequest":{"properties":{"agentId":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agentid","description":"Agent that runs the routine"},"title":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Title","description":"What the routine is called"},"instruction":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Instruction","description":"What the agent is asked to do each run"},"deliveryConversationId":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Deliveryconversationid","description":"Re-point delivery; the new conversation must also be readable"},"weekdays":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Weekdays","description":"Days to run on (0-6)"},"localTime":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Localtime","description":"Local run time `HH:MM`"},"timezone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Timezone","description":"IANA timezone the local time is read in"},"enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Enabled","description":"Turn the routine on or off"},"triggerKind":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Triggerkind","description":"`schedule` or `event`"},"trigger":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Trigger","description":"Trigger config, for `event` routines"},"eventPolicy":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Eventpolicy","description":"Optional event-handling policy"}},"additionalProperties":false,"type":"object","title":"WorkRoutinePatchRequest","description":"Changes to one routine. Omitted fields keep their stored value."},"WorkRoutineRun":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id","description":"Run id"},"startedAt":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Startedat","description":"When the run started"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"How the run ended, or that it is still going"}},"additionalProperties":true,"type":"object","title":"WorkRoutineRun","description":"One entry in a routine's run ledger."},"WorkRoutineRunList":{"properties":{"runs":{"items":{"$ref":"#/components/schemas/WorkRoutineRun"},"type":"array","title":"Runs","description":"Runs, newest first"}},"type":"object","title":"WorkRoutineRunList","description":"The event-run ledger for one routine — telemetry only."},"WorkRoutineRunNowRequest":{"properties":{"sampleEvent":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Sampleevent","description":"Example event payload; treated as data, never as instructions. `event` routines only."}},"additionalProperties":false,"type":"object","title":"WorkRoutineRunNowRequest","description":"An optional sample event to run an `event` routine against."},"WorkRoutineRunResult":{"properties":{"runId":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Runid","description":"Ledger id of this manual run"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"Always `running` on this response"},"messageId":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Messageid","description":"The message the run posted"},"conversationId":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Conversationid","description":"Where it was posted"},"startedAt":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Startedat","description":"When the run started"},"runsPath":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Runspath","description":"Developer API path to poll for this run's outcome"}},"additionalProperties":true,"type":"object","title":"WorkRoutineRunResult","description":"A run-now receipt: what was posted, and where to watch it finish.\n\nThe run is asynchronous — the instruction is posted immediately and the\nagent answers in the background — so this returns the ledger id to poll\nrather than the answer. ``status`` is ``running`` here and moves to ``ok``\nor ``failed`` on the row this points at."},"WorkSearchHit":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id","description":"Message or event id"},"conversation":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Conversation","description":"Conversation the hit belongs to"},"text":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Text","description":"Matched text"}},"additionalProperties":true,"type":"object","title":"WorkSearchHit","description":"One search hit — a message or an event, with its conversation."},"WorkSearchResults":{"properties":{"query":{"type":"string","title":"Query","description":"The query that was run, as the server normalized it"},"hits":{"items":{"$ref":"#/components/schemas/WorkSearchHit"},"type":"array","title":"Hits","description":"Ranked hits, capped by the server maximum"}},"type":"object","required":["query"],"title":"WorkSearchResults","description":"Everything this credential may read that matches the query."},"WorkSidebarPreferences":{"properties":{"preferences":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Preferences","description":"The ordering as stored"}},"additionalProperties":true,"type":"object","title":"WorkSidebarPreferences","description":"This principal's stored sidebar ordering."},"WorkSidebarPreferencesRequest":{"properties":{"channels":{"type":"string","enum":["alpha","recent"],"title":"Channels"},"directMessages":{"type":"string","enum":["alpha","recent"],"title":"Directmessages"}},"additionalProperties":false,"type":"object","required":["channels","directMessages"],"title":"WorkSidebarPreferencesRequest","description":"How this person wants their own sidebar ordered.\n\nBoth halves are required and closed-vocabulary, exactly as\n`normalizeSidebarSortMode` requires them (`index.ts:10838`): a partial\nwrite would leave the other half at whatever a previous client wrote and\nmake the response a lie about the stored state."},"WorkSignalPromoteRequest":{"properties":{"signalEventId":{"type":"string","maxLength":128,"minLength":1,"title":"Signaleventid"}},"additionalProperties":false,"type":"object","required":["signalEventId"],"title":"WorkSignalPromoteRequest","description":"Turn one revenue signal into an accountable Work turn."},"WorkSignalPromoted":{"properties":{"message":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Message","description":"The stored message that carries the turn"},"duplicate":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Duplicate","description":"True when this signal had already been promoted"}},"additionalProperties":true,"type":"object","title":"WorkSignalPromoted","description":"The message a signal promotion sent into `#work`."},"WorkSignalState":{"properties":{"event":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Event","description":"The room event the write appended"},"duplicate":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Duplicate","description":"True when the signal already held the requested state"}},"additionalProperties":true,"type":"object","title":"WorkSignalState","description":"One revenue signal after being snoozed or dismissed."},"WorkSignalStateRequest":{"properties":{"signalEventId":{"type":"string","maxLength":128,"minLength":1,"title":"Signaleventid"},"action":{"type":"string","enum":["snooze","dismiss"],"title":"Action"}},"additionalProperties":false,"type":"object","required":["signalEventId","action"],"title":"WorkSignalStateRequest","description":"Snooze or dismiss one revenue signal."},"WorkTeamHqHistory":{"properties":{"days":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Days","description":"The dates in the window, oldest first"},"reps":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Reps","description":"Per-rep series; null for a day that was not measured (a gap is not a zero)"},"source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source","description":"`live`, `cached` or `unavailable`"}},"additionalProperties":true,"type":"object","title":"WorkTeamHqHistory","description":"Per-rep daily series behind the board's sparklines, deltas and streaks."},"WorkTeamHqLeaderboard":{"properties":{"period":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Period","description":"`day` or `month`"},"generatedAt":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Generatedat","description":"When this response was built"},"measuredAt":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Measuredat","description":"When the rows were measured; null when unavailable"},"rows":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Rows","description":"One row per rep"},"source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source","description":"`live`, `cached`, `partial` or `unavailable`"},"degradedMetrics":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Degradedmetrics","description":"Columns that failed to measure; absent from every row rather than zero"},"goals":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Goals","description":"Per role-group goals, or null"}},"additionalProperties":true,"type":"object","title":"WorkTeamHqLeaderboard","description":"One Team HQ board over the organization's own SDR analytics."},"WorkTickerEvents":{"properties":{"events":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Events","description":"Moments, newest first"},"source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source","description":"`live` for the receipts drill-down"}},"additionalProperties":true,"type":"object","title":"WorkTickerEvents","description":"Team HQ ticker moments, newest first."},"WorkbenchBindingItem":{"properties":{"node_id":{"type":"string","title":"Node Id","description":"The workflow node whose output feeds the column."},"output_path":{"type":"string","title":"Output Path","description":"Dot path into that node's output."},"column_name":{"type":"string","title":"Column Name","description":"Display name of the column."},"column_type":{"type":"string","enum":["computed","ai","enrichment","state","action","review"],"title":"Column Type","description":"How the grid treats the column."},"display_mode":{"type":"string","title":"Display Mode","description":"How the cell renders.","default":"text"},"sort_order":{"type":"integer","title":"Sort Order","description":"Position among the bound columns.","default":0},"config":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Config","description":"Column-type settings."}},"type":"object","required":["node_id","output_path","column_name","column_type"],"title":"WorkbenchBindingItem","description":"One workflow output rendered as one grid column."},"WorkbenchColumnCreateRequest":{"properties":{"name":{"type":"string","maxLength":255,"minLength":1,"pattern":"^[a-z][a-z0-9_]*$","title":"Name","description":"Machine name: lowercase, starting with a letter. This is the key row data is addressed by, which is why it is constrained while `display_name` is not."},"display_name":{"type":"string","maxLength":255,"minLength":1,"title":"Display Name"},"data_type":{"type":"string","enum":["text","number","boolean","json"],"title":"Data Type","default":"text"},"column_type":{"type":"string","enum":["data","formula","raw_json"],"title":"Column Type","default":"data"},"field_path":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Field Path","description":"Path into a raw_json source column."},"source":{"type":"string","title":"Source","default":"manual"},"source_column_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Source Column Id"},"formula":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Formula","description":"Required for a formula column."}},"type":"object","required":["name","display_name"],"title":"WorkbenchColumnCreateRequest"},"WorkbenchColumnMappingRequest":{"properties":{"mapping_target":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Mapping Target"}},"type":"object","title":"WorkbenchColumnMappingRequest","description":"Point a column at a CRM field so export knows where its values go.\n\n`null` clears the mapping, which is why the field is optional rather than\nrequired - an unmapped column is a real state, not a missing argument."},"WorkbenchCreditValidationRequest":{"properties":{"column_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Column Id"},"group_id":{"anyOf":[{"type":"string","maxLength":255,"minLength":1},{"type":"null"}],"title":"Group Id"},"all_columns":{"type":"boolean","title":"All Columns","default":false},"row_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Row Ids","description":"OMIT to price EVERY row."},"exclude_row_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array"},{"type":"null"}],"title":"Exclude Row Ids"},"status_filter":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status Filter"}},"type":"object","title":"WorkbenchCreditValidationRequest","description":"Price a run before starting it. FREE.\n\nAt most one of `column_id`, `group_id` and `all_columns`. None prices the\ntable's default AI pass."},"WorkbenchExportRequest":{"properties":{"list_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"List Id","description":"Existing list to export into."},"create_new_list":{"type":"boolean","title":"Create New List","default":false},"new_list_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"New List Name"},"entity_type":{"type":"string","enum":["contact","company"],"title":"Entity Type","default":"contact"},"row_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array","maxItems":100000},{"type":"null"}],"title":"Row Ids"},"exclude_row_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array","maxItems":100000},{"type":"null"}],"title":"Exclude Row Ids"},"export_verified_only":{"type":"boolean","title":"Export Verified Only","description":"Only rows whose email passed verification.","default":false},"export_filter":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Export Filter"}},"type":"object","title":"WorkbenchExportRequest","description":"Export rows to an audience list."},"WorkbenchPage":{"properties":{"items":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Items"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"WorkbenchPage","description":"A page of rows, or a list of columns, exactly as the app returns it.\n\nRows and columns stay open dicts: a Workbench table's columns are defined\nby the CUSTOMER at runtime. There is no schema to pin, and inventing one\nwould make the product unusable through this API."},"WorkbenchPipelineBranchStep":{"properties":{"id":{"type":"string","maxLength":255,"minLength":1,"title":"Id"},"type":{"type":"string","enum":["ai_group","waterfall","formula","branch","export_to_list"],"title":"Type"},"name":{"type":"string","maxLength":255,"minLength":1,"title":"Name"},"enabled":{"type":"boolean","title":"Enabled","default":true},"group_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Group Id"},"column_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Column Id"},"template":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Template"},"inline_config":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Inline Config"},"conditions":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Conditions"},"if_steps":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"If Steps"},"else_steps":{"items":{"additionalProperties":true,"type":"object"},"type":"array","title":"Else Steps"}},"type":"object","required":["id","type","name"],"title":"WorkbenchPipelineBranchStep","description":"A step inside a branch.\n\nIts own `if_steps` / `else_steps` are open objects in this schema: the app\nnests steps without limit, and a self-referencing schema is not publishable.\nThey are still validated as steps by the app."},"WorkbenchPipelineStep":{"properties":{"id":{"type":"string","maxLength":255,"minLength":1,"title":"Id"},"type":{"type":"string","enum":["ai_group","waterfall","formula","branch","export_to_list"],"title":"Type"},"name":{"type":"string","maxLength":255,"minLength":1,"title":"Name"},"enabled":{"type":"boolean","title":"Enabled","default":true},"group_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Group Id"},"column_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Column Id"},"template":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Template"},"inline_config":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Inline Config"},"conditions":{"anyOf":[{"items":{"additionalProperties":true,"type":"object"},"type":"array"},{"type":"null"}],"title":"Conditions"},"if_steps":{"items":{"$ref":"#/components/schemas/WorkbenchPipelineBranchStep"},"type":"array","title":"If Steps"},"else_steps":{"items":{"$ref":"#/components/schemas/WorkbenchPipelineBranchStep"},"type":"array","title":"Else Steps"}},"type":"object","required":["id","type","name"],"title":"WorkbenchPipelineStep","description":"One step. A `branch` step runs `if_steps` or `else_steps`."},"WorkbenchRowCreateRequest":{"properties":{"data":{"additionalProperties":true,"type":"object","title":"Data","description":"Column machine name -> value."},"raw_source_column_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Raw Source Column Id"}},"type":"object","title":"WorkbenchRowCreateRequest"},"WorkbenchRowUpdateRequest":{"properties":{"field":{"type":"string","maxLength":255,"minLength":1,"title":"Field"},"value":{"title":"Value"}},"type":"object","required":["field","value"],"title":"WorkbenchRowUpdateRequest","description":"Set ONE field on one row - the grid's cell edit."},"WorkbenchRowsDeleteRequest":{"properties":{"row_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array","maxItems":100000},{"type":"null"}],"title":"Row Ids"},"select_all":{"type":"boolean","title":"Select All","default":false},"exclude_row_ids":{"anyOf":[{"items":{"type":"integer"},"type":"array","maxItems":100000},{"type":"null"}],"title":"Exclude Row Ids"}},"type":"object","title":"WorkbenchRowsDeleteRequest","description":"Delete rows by id, or every row EXCEPT a set.\n\n`select_all` is EXPLICIT rather than inferred from an empty `row_ids`,\nmirroring the app - so a client bug can never turn \"nothing selected\" into\n\"delete the whole table\". This surface keeps that guarantee rather than\naccepting a bare empty list as a delete-everything."},"WorkbenchSearchImportRequest":{"properties":{"filters":{"items":{"additionalProperties":true,"type":"object"},"type":"array","minItems":1,"title":"Filters"},"limit":{"type":"integer","maximum":50000.0,"minimum":1.0,"title":"Limit","default":500},"max_result":{"anyOf":[{"type":"integer","maximum":50000.0,"minimum":1.0},{"type":"null"}],"title":"Max Result"},"max_employees_per_company":{"anyOf":[{"type":"integer","maximum":1000.0,"minimum":1.0},{"type":"null"}],"title":"Max Employees Per Company"},"skip_duplicates":{"type":"boolean","title":"Skip Duplicates","default":true},"return_inserted_ids":{"type":"boolean","title":"Return Inserted Ids","default":false},"raw_source_column_id":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Raw Source Column Id"}},"type":"object","required":["filters"],"title":"WorkbenchSearchImportRequest","description":"Import people from a search into the table as LOCKED rows.\n\nEach row costs a credit to unlock (`POST .../unlock-rows`)."},"WorkbenchTable":{"properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id"},"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"},"entity_type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Entity Type","description":"contact or company."},"row_count":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Row Count"},"created_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Created At"},"updated_at":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Updated At"}},"additionalProperties":true,"type":"object","title":"WorkbenchTable","description":"One staging table."},"WorkbenchTableCreateRequest":{"properties":{"name":{"type":"string","minLength":1,"title":"Name","description":"Table name."},"entity_type":{"anyOf":[{"type":"string","enum":["contact","company"]},{"type":"null"}],"title":"Entity Type","description":"What the rows will become on export. Settable once, at creation."},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"}},"type":"object","required":["name"],"title":"WorkbenchTableCreateRequest"},"WorkbenchTableList":{"properties":{"tables":{"items":{"$ref":"#/components/schemas/WorkbenchTable"},"type":"array","title":"Tables"},"total":{"type":"integer","title":"Total","default":0}},"additionalProperties":true,"type":"object","title":"WorkbenchTableList"},"WorkbenchTableUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"}},"type":"object","title":"WorkbenchTableUpdateRequest","description":"Rename or re-describe. `entity_type` is deliberately absent - it decides\nhow rows export and is fixed at creation."},"WorkflowConnectionCreateRequest":{"properties":{"kind":{"type":"string","enum":["mcp","api","any"],"title":"Kind","description":"What the destination is: `mcp`, `api` or `any`.","default":"any"},"value":{"type":"string","minLength":1,"title":"Value","description":"Approved host (`api.hubspot.com`), `.hubspot.com` for its subdomains, or `stdio:<command>`."},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description","description":"Why this destination is approved."},"enabled":{"type":"boolean","title":"Enabled","description":"Approved and active.","default":true}},"additionalProperties":false,"type":"object","required":["value"],"title":"WorkflowConnectionCreateRequest","description":"Approve an external destination (an MCP server or an API host) for the organisation's workflows.\n\nThe organisation is the key's. `created_by` is not accepted: the approving admin is recorded from the key."},"WorkflowConnectionUpdateRequest":{"properties":{"enabled":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Enabled"},"description":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Description"}},"additionalProperties":false,"type":"object","title":"WorkflowConnectionUpdateRequest","description":"Enable or disable an approved destination, or re-describe it. Disabling revokes it."},"WorkflowStepInput":{"properties":{"action":{"type":"string","enum":["email_host","email_attendee","email_address"],"title":"Action"},"template":{"type":"string","enum":["reminder","custom","cancelled","rescheduled","completed","rating"],"title":"Template","default":"reminder"},"email_subject":{"anyOf":[{"type":"string","maxLength":500},{"type":"null"}],"title":"Email Subject"},"reminder_body":{"anyOf":[{"type":"string","maxLength":20000},{"type":"null"}],"title":"Reminder Body"},"send_to":{"anyOf":[{"type":"string","format":"email"},{"type":"null"}],"title":"Send To"},"sender":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Sender"},"include_calendar_event":{"type":"boolean","title":"Include Calendar Event","default":false}},"type":"object","required":["action"],"title":"WorkflowStepInput"},"WorkflowTriggerObject":{"properties":{"object_definition_id":{"type":"string","format":"uuid","title":"Object Definition Id"},"object_slug":{"type":"string","title":"Object Slug"},"label":{"type":"string","title":"Label"},"kind":{"type":"string","enum":["object","process_list"],"title":"Kind"},"list_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"List Name"},"parent_label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Parent Label"}},"type":"object","required":["object_definition_id","object_slug","label","kind"],"title":"WorkflowTriggerObject","description":"An object a record trigger can watch. A process list's entries are records of its (hidden) backing object."},"WorkflowTriggerObjectsResponse":{"properties":{"objects":{"items":{"$ref":"#/components/schemas/WorkflowTriggerObject"},"type":"array","title":"Objects"}},"type":"object","required":["objects"],"title":"WorkflowTriggerObjectsResponse"},"WorkspaceMemberInput":{"properties":{"user_id":{"type":"string","maxLength":255,"minLength":1,"title":"User Id"},"role":{"type":"string","enum":["member","manager"],"title":"Role","description":"member | manager","default":"member"}},"type":"object","required":["user_id"],"title":"WorkspaceMemberInput","description":"One member in a team's single-save membership list."},"WorkspaceSearchListPayload":{"properties":{"items":{"items":{},"type":"array","title":"Items"}},"additionalProperties":true,"type":"object","title":"WorkspaceSearchListPayload","description":"A list result under `items`."},"WorkspaceSearchPayload":{"properties":{},"additionalProperties":true,"type":"object","title":"WorkspaceSearchPayload","description":"Search results, grouped the way the app groups them."},"WorkspaceSearchRequest":{"properties":{"query":{"type":"string","title":"Query"},"search_type":{"type":"string","enum":["semantic","exact","hybrid","auto"],"title":"Search Type","description":"`auto` picks keyword or semantic from the wording of the query.","default":"auto"},"filters":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Filters"},"k":{"type":"integer","title":"K","description":"How many results.","default":20}},"type":"object","required":["query"],"title":"WorkspaceSearchRequest"},"XAccountSelectionRequest":{"properties":{"ad_account_id":{"type":"string","maxLength":64,"minLength":1,"title":"Ad Account Id"},"funding_instrument_id":{"type":"string","maxLength":64,"title":"Funding Instrument Id","default":""},"as_user_id":{"type":"string","maxLength":64,"title":"As User Id","default":""}},"type":"object","required":["ad_account_id"],"title":"XAccountSelectionRequest","description":"The org's X ad account (and optionally payment method / promotable user)\nto launch X campaigns into. Validated against what the X login can reach."},"XApiCredentialsRequest":{"properties":{"api_key":{"type":"string","minLength":1,"title":"Api Key","description":"X Developer App API key (consumer key)."},"api_secret":{"type":"string","minLength":1,"title":"Api Secret","description":"X Developer App API secret."}},"type":"object","required":["api_key","api_secret"],"title":"XApiCredentialsRequest","description":"An X developer app's key and secret.\n\nWRITE-ONLY. Neither value, nor the bearer token derived from them, is ever\nreturned by any route on this surface - `GET /social-listeners/integrations/x`\nreports whether a connection exists, not what it is."},"appointments__domain__entities__UpdateSequenceRequest":{"properties":{"sequence_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Sequence Id"}},"type":"object","title":"UpdateSequenceRequest","description":"Associate a booking with a sequencer sequence (or detach when null).\n\n`sequence_id` is the `seqsequences.id` UUID. Persisted under\n`booking.metadata_['campaignId']` — same key the public booking flow\npopulates from the `?campaignId=` URL param at create time."},"developer_api__interfaces__dtos__inbox__TagRequest":{"properties":{"tag_ids":{"items":{"type":"string"},"type":"array","title":"Tag Ids","description":"Tag IDs to associate with the thread"}},"type":"object","required":["tag_ids"],"title":"TagRequest"},"developer_api__interfaces__dtos__inbox_collab__TagRequest":{"properties":{"tag_id":{"type":"string","title":"Tag Id","description":"The tag to attach. It must already exist."}},"type":"object","required":["tag_id"],"title":"TagRequest","description":"Attach an existing tag to a conversation."},"developer_api__interfaces__v1__cli_campaigns_router__CampaignCreateRequest":{"properties":{"name":{"type":"string","title":"Name","description":"Campaign name"},"category":{"type":"string","title":"Category","description":"Campaign category","default":"Outbound"},"brief":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Brief","description":"Campaign brief"},"core_concept":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Core Concept","description":"Core concept"},"primary_hook":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Primary Hook","description":"Primary hook text"},"target_persona":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Persona","description":"Target persona"},"goal":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Goal","description":"Campaign goal"}},"type":"object","required":["name"],"title":"CampaignCreateRequest"},"developer_api__interfaces__v1__cli_campaigns_router__CampaignUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Name","description":"Campaign name"},"brief":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Brief","description":"Campaign brief"},"core_concept":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Core Concept","description":"Core concept"},"primary_hook":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Primary Hook","description":"Primary hook text"},"target_persona":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Target Persona","description":"Target persona"},"category":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Category","description":"Campaign category"},"goal":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Goal","description":"Campaign goal"}},"type":"object","title":"CampaignUpdateRequest"},"developer_api__interfaces__v1__gtm_campaigns_router__CampaignCreateRequest":{"properties":{"name":{"type":"string","maxLength":255,"title":"Name","description":"Campaign name"},"category":{"type":"string","maxLength":100,"title":"Category","description":"Campaign category","default":"Outbound"},"brief":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Brief","description":"Campaign brief"},"core_concept":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Core Concept","description":"Core concept"},"primary_hook":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Primary Hook","description":"Primary hook text"},"target_persona":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Target Persona","description":"Target persona"},"goal":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Goal","description":"Campaign goal"},"audience_list_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Audience List Id","description":"If provided, attaches this list ID to cb_campaigns.audience_list_id at create time."},"target_channels":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Target Channels","description":"Channels the campaign will use, e.g. ['email'], ['email','linkedin']. Drives which copy documents the auto-generator creates. Defaults to ['email']."},"execution_targets":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Execution Targets","description":"Execution destinations: sequencer, dialer, or content_only."},"secondary_hooks":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Secondary Hooks","description":"Additional hook variations to seed the campaign idea with."},"auto_generate_documents":{"type":"boolean","title":"Auto Generate Documents","description":"When True, dispatches the Celery campaign-content generator asynchronously after creation: the paired cb_campaign_ideas row is inserted (so the FE workbench sees the campaign), cb_campaign_metadata is created, the campaign starts in status='copy_in_progress', and flips to 'active' once docs are ready (~60-90s). Default is False to preserve byte-for-byte backwards compatibility with the original bare-bones draft behavior — the MCP tool wrapper sets True explicitly to opt into Studio parity.","default":false}},"type":"object","required":["name"],"title":"CampaignCreateRequest"},"developer_api__interfaces__v1__gtm_campaigns_router__CampaignUpdateRequest":{"properties":{"name":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Name","description":"Campaign name"},"brief":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Brief","description":"Campaign brief"},"core_concept":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Core Concept","description":"Core concept"},"primary_hook":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Primary Hook","description":"Primary hook text"},"target_persona":{"anyOf":[{"type":"string","maxLength":200},{"type":"null"}],"title":"Target Persona","description":"Target persona"},"category":{"anyOf":[{"type":"string","maxLength":100},{"type":"null"}],"title":"Category","description":"Campaign category"},"goal":{"anyOf":[{"type":"string","maxLength":255},{"type":"null"}],"title":"Goal","description":"Campaign goal"},"target_channels":{"anyOf":[{"items":{"type":"string"},"type":"array"},{"type":"null"}],"title":"Target Channels","description":"Replace the campaign's channels, e.g. ['email','linkedin']. Accepted values: email, linkedin, phone, voice_ai, sms. Omit to leave them unchanged. Existing documents and steps are not deleted."}},"type":"object","title":"CampaignUpdateRequest"},"developer_api__interfaces__v1__gtm_campaigns_router__UpdateSequenceRequest":{"properties":{"steps":{"items":{"$ref":"#/components/schemas/SequenceStepRef"},"type":"array","title":"Steps"}},"type":"object","required":["steps"],"title":"UpdateSequenceRequest"}},"securitySchemes":{"HTTPBearer":{"type":"http","scheme":"bearer"},"BearerAuth":{"type":"http","scheme":"bearer","description":"Org API key: `Authorization: Bearer <api_key>`"}}},"security":[{"BearerAuth":[]}]}